Java HashSet Class: A Beginner's Guide

Introduction

Hello, future Java developers! Today, we're going to dive into the wonderful world of HashSet in Java. Don't worry if you're new to programming; I'll guide you through this journey step by step, just like I've done for countless students over my years of teaching. Think of HashSet as a magic box that can store unique items - no duplicates allowed! It's like having a special drawer where you can only put one of each type of sock. Let's get started!

Java - HashSet

Class Declaration

In Java, HashSet is part of the Java Collections Framework. To use it, we first need to import it:

import java.util.HashSet;

The basic declaration of a HashSet looks like this:

HashSet<E> hs = new HashSet<E>();

Here, 'E' is a placeholder for the type of elements you want to store in your HashSet. For example, if you want to store strings:

HashSet<String> fruitBasket = new HashSet<String>();

Parameters

When creating a HashSet, you can specify two optional parameters:

  1. Initial capacity: The number of "buckets" HashSet will use to store elements.
  2. Load factor: A measure of how full the HashSet can be before it's automatically increased in size.

Don't worry too much about these for now. Think of them as advanced settings for your magic box!

Class Constructors

HashSet provides four constructors. Let's look at each of them:

// Constructor 1: Creates an empty HashSet with default initial capacity (16) and load factor (0.75)
HashSet<String> set1 = new HashSet<>();

// Constructor 2: Creates a HashSet containing elements of the specified collection
Collection<String> collection = Arrays.asList("Apple", "Banana", "Cherry");
HashSet<String> set2 = new HashSet<>(collection);

// Constructor 3: Creates an empty HashSet with the specified initial capacity and default load factor (0.75)
HashSet<String> set3 = new HashSet<>(20);

// Constructor 4: Creates an empty HashSet with the specified initial capacity and load factor
HashSet<String> set4 = new HashSet<>(20, 0.8f);

Class Methods

Here's a table of the most commonly used HashSet methods:

Method Description
add(E e) Adds the specified element to this set if it is not already present
clear() Removes all of the elements from this set
contains(Object o) Returns true if this set contains the specified element
isEmpty() Returns true if this set contains no elements
remove(Object o) Removes the specified element from this set if it is present
size() Returns the number of elements in this set

Methods Inherited

HashSet inherits methods from its parent classes. Some notable ones include:

  • From Set: addAll(), containsAll(), equals(), hashCode(), removeAll(), retainAll()
  • From Collection: iterator(), toArray()
  • From Object: clone(), finalize(), getClass(), notify(), notifyAll(), wait()

Adding Elements to a HashSet Example

Let's put our knowledge into practice with a fun example. Imagine we're creating a program to keep track of unique ice cream flavors in our shop:

import java.util.HashSet;

public class IceCreamShop {
    public static void main(String[] args) {
        // Create a new HashSet to store ice cream flavors
        HashSet<String> flavors = new HashSet<>();

        // Add some flavors
        flavors.add("Vanilla");
        flavors.add("Chocolate");
        flavors.add("Strawberry");
        flavors.add("Mint Chip");

        // Try adding a duplicate
        boolean added = flavors.add("Vanilla");

        System.out.println("Vanilla added again? " + added);
        System.out.println("Our ice cream flavors: " + flavors);
        System.out.println("We have " + flavors.size() + " unique flavors!");

        // Check if we have a specific flavor
        String searchFlavor = "Rocky Road";
        if (flavors.contains(searchFlavor)) {
            System.out.println("Yes, we have " + searchFlavor + "!");
        } else {
            System.out.println("Sorry, we don't have " + searchFlavor + ".");
        }

        // Remove a flavor
        flavors.remove("Strawberry");
        System.out.println("Updated flavors after removing Strawberry: " + flavors);
    }
}

Output

When you run this program, you'll see something like this:

Vanilla added again? false
Our ice cream flavors: [Vanilla, Mint Chip, Chocolate, Strawberry]
We have 4 unique flavors!
Sorry, we don't have Rocky Road.
Updated flavors after removing Strawberry: [Vanilla, Mint Chip, Chocolate]

Let's break down what happened:

  1. We created a HashSet called flavors to store our ice cream flavors.
  2. We added four flavors: Vanilla, Chocolate, Strawberry, and Mint Chip.
  3. We tried to add Vanilla again, but add() returned false because HashSet doesn't allow duplicates.
  4. We printed out all our flavors. Notice the order might be different from how we added them - HashSet doesn't maintain insertion order.
  5. We checked if we had Rocky Road flavor using contains(). We didn't, so it printed a "sorry" message.
  6. Finally, we removed Strawberry and printed the updated set of flavors.

And there you have it! You've just created your first HashSet and used some of its most important methods. Remember, HashSet is great when you need to store unique elements and don't care about the order. It's like a bag of marbles where each marble is a different color - you can easily check if you have a specific color, but you can't control the order they come out when you dump the bag.

As you continue your Java journey, you'll find HashSet incredibly useful in many scenarios. Keep practicing, and soon you'll be a HashSet pro! Happy coding!

Credits: Image by storyset