Home  >  Article  >  Java  >  Detailed introduction to Java collection HashSet

Detailed introduction to Java collection HashSet

黄舟
黄舟Original
2017-03-13 17:45:041834browse

HashSet is a set without duplicate elements. HashSet is implemented by HashMap and does not guarantee the order of elements. HashSet allows the use of null elements. . HashSet is not thread-safe. When multiple threads access HashSet at the same time, problems will occur. The solution is to perform synchronization operations on the object that naturally encapsulates the Set. You can also use the Collections.synchronizedSet method to wrap the set.

Set s=Collectins.synchronizedSet(new HashSet()).

HashSet inheritance implementation diagram:


From the diagram we can see:

(1) HashSet inherits from AbstractSet, and implements Setinterface.

(2) HashSet is essentially a set without duplicate elements, implemented through HashMap. There is a map variable of HashMap in HashSet, and the operationfunction of HashSet is actually implemented through map. HashSet is the key that stores the value as a HashMap.


HashSet main function:


add(E object)
clear()
Object clone()
contains(Object object)
isEmpty()
Iteratora8093152e673feb7aba1828c43532094 iterator()
remove(Object object)
size()

HashSet traversal method:

(1) Traverse the HashSet through Iterator iteration: first obtain the iterator of the HashSet according to iterator(), and iterate to obtain each element.


(Iterator iterator = set.iterator()iterator.hasNext()) 
    {
        iterator.next()}

(2) Traverse the HashSet through for-each: first obtain the array corresponding to the element collection of the HashSet through toArray(), and then traverse the array to obtain the elements.


String[] arr = (String[])set.toArray(String[])(String str:arr)
   {
       System.out.printf(str)   }

HashSet sample code:


Hello {

(String[] args) Exception {
() }

() {
HashSet set = HashSet()set.add()set.add()set.add()set.add()set.add()System..printf(set.size())System..printf(set.contains())System..printf(set.contains())set.remove()String[] arr = (String[])set.toArray(String[])(String str:arr)
            System..printf(str)HashSet otherset = HashSet()otherset.add()otherset.add()otherset.add()HashSet removeset = (HashSet)set.clone()removeset.removeAll(otherset)System..printf(removeset)HashSet retainset = (HashSet)set.clone()retainset.retainAll(otherset)System..printf(retainset)(Iterator iterator = set.iterator()iterator.hasNext())
            System..printf(iterator.next())set.clear()System..printf(set.isEmpty()?:)}
}

Result:

size : 5
HashSet contains a :true
HashSet contains g :false
for each : a
for each : b
for each : c
for each : d
removeset : [a, d]
retainset : [b, c]
iterator : a
iterator : b
iterator : c
iterator : d
set is empty

HashSet source code based on Java8 :


public class HashSet1a4db2c2c2313771e5742b6debf617a1 extends AbstractSet1a4db2c2c2313771e5742b6debf617a1
        implements Set1a4db2c2c2313771e5742b6debf617a1, Cloneable, java.io.Serializable
{
    static final long serialVersionUID = -5024744406713321676L;
    private transient HashMapc81ac021d9fe376b0afca3578d66e836 map;//HashSet是利用map来存储数据
    private static final Object PRESENT = new Object();

    /**
     * Constructs a new, empty set; the backing 78f983dbc27872ba42409adefe5049d9HashMapd98ca7951c814b9263d12f482df06c69 instance has
     * default initial capacity (16) and load factor (0.75).
     */
    //构造一个空Set
    public HashSet() {
        map = new HashMapa8093152e673feb7aba1828c43532094();
    }

    /**
     * Constructs a new set containing the elements in the specified
     * collection.  The 78f983dbc27872ba42409adefe5049d9HashMapd98ca7951c814b9263d12f482df06c69 is created with default load factor
     * (0.75) and an initial capacity sufficient to contain the elements in
     * the specified collection.
     *
     * @param c the collection whose elements are to be placed into this set
     * @throws NullPointerException if the specified collection is null
     */
    //构造一个有初始参数c的构造函数
    public HashSet(Collection216930c0ab3d232ff5eb2d5ba8cef959 c) {
        map = new HashMapa8093152e673feb7aba1828c43532094(Math.max((int) (c.size()/.75f) + 1, 16));
        addAll(c);
    }

    /**
     * Constructs a new, empty set; the backing 78f983dbc27872ba42409adefe5049d9HashMapd98ca7951c814b9263d12f482df06c69 instance has
     * the specified initial capacity and the specified load factor.
     *
     * @param      initialCapacity   the initial capacity of the hash map
     * @param      loadFactor        the load factor of the hash map
     * @throws     IllegalArgumentException if the initial capacity is less
     *             than zero, or if the load factor is nonpositive
     */
    //初始容量和加载因子的构造函数,其实是HashMap的构造函数
    public HashSet(int initialCapacity, float loadFactor) {
        map = new HashMapa8093152e673feb7aba1828c43532094(initialCapacity, loadFactor);
    }

    /**
     * Constructs a new, empty set; the backing 78f983dbc27872ba42409adefe5049d9HashMapd98ca7951c814b9263d12f482df06c69 instance has
     * the specified initial capacity and default load factor (0.75).
     *
     * @param      initialCapacity   the initial capacity of the hash table
     * @throws     IllegalArgumentException if the initial capacity is less
     *             than zero
     */
    //构造初始容量的构造函数
    public HashSet(int initialCapacity) {
        map = new HashMapa8093152e673feb7aba1828c43532094(initialCapacity);
    }

    /**
     * Constructs a new, empty linked hash set.  (This package private
     * constructor is only used by LinkedHashSet.) The backing
     * HashMap instance is a LinkedHashMap with the specified initial
     * capacity and the specified load factor.
     *
     * @param      initialCapacity   the initial capacity of the hash map
     * @param      loadFactor        the load factor of the hash map
     * @param      dummy             ignored (distinguishes this
     *             constructor from other int, float constructor.)
     * @throws     IllegalArgumentException if the initial capacity is less
     *             than zero, or if the load factor is nonpositive
     */
    //构造一个空的LinkedHashMap
    HashSet(int initialCapacity, float loadFactor, boolean dummy) {
        map = new LinkedHashMapa8093152e673feb7aba1828c43532094(initialCapacity, loadFactor);
    }

    /**
     * Returns an iterator over the elements in this set.  The elements
     * are returned in no particular order.
     *
     * @return an Iterator over the elements in this set
     * @see ConcurrentModificationException
     */
    //返回key的迭代
    public Iterator1a4db2c2c2313771e5742b6debf617a1 iterator() {
        return map.keySet().iterator();
    }

    /**
     * Returns the number of elements in this set (its cardinality).
     *
     * @return the number of elements in this set (its cardinality)
     */
    //大小
    public int size() {
        return map.size();
    }

    /**
     * Returns 78f983dbc27872ba42409adefe5049d9trued98ca7951c814b9263d12f482df06c69 if this set contains no elements.
     *
     * @return 78f983dbc27872ba42409adefe5049d9trued98ca7951c814b9263d12f482df06c69 if this set contains no elements
     */
    //判断是否为空
    public boolean isEmpty() {
        return map.isEmpty();
    }

    /**
     * Returns 78f983dbc27872ba42409adefe5049d9trued98ca7951c814b9263d12f482df06c69 if this set contains the specified element.
     * More formally, returns 78f983dbc27872ba42409adefe5049d9trued98ca7951c814b9263d12f482df06c69 if and only if this set
     * contains an element 78f983dbc27872ba42409adefe5049d9ed98ca7951c814b9263d12f482df06c69 such that
     * 78f983dbc27872ba42409adefe5049d9(o==null ? e==null : o.equals(e))d98ca7951c814b9263d12f482df06c69.
     *
     * @param o element whose presence in this set is to be tested
     * @return 78f983dbc27872ba42409adefe5049d9trued98ca7951c814b9263d12f482df06c69 if this set contains the specified element
     */
    //判断是否包含某个对象
    public boolean contains(Object o) {
        return map.containsKey(o);
    }

    /**
     * Adds the specified element to this set if it is not already present.
     * More formally, adds the specified element 78f983dbc27872ba42409adefe5049d9ed98ca7951c814b9263d12f482df06c69 to this set if
     * this set contains no element 78f983dbc27872ba42409adefe5049d9e2d98ca7951c814b9263d12f482df06c69 such that
     * 78f983dbc27872ba42409adefe5049d9(e==null ? e2==null : e.equals(e2))d98ca7951c814b9263d12f482df06c69.
     * If this set already contains the element, the call leaves the set
     * unchanged and returns 78f983dbc27872ba42409adefe5049d9falsed98ca7951c814b9263d12f482df06c69.
     *
     * @param e element to be added to this set
     * @return 78f983dbc27872ba42409adefe5049d9trued98ca7951c814b9263d12f482df06c69 if this set did not already contain the specified
     * element
     */
    //增加对象
    public boolean add(E e) {
        return map.put(e, PRESENT)==null;
    }

    /**
     * Removes the specified element from this set if it is present.
     * More formally, removes an element 78f983dbc27872ba42409adefe5049d9ed98ca7951c814b9263d12f482df06c69 such that
     * 78f983dbc27872ba42409adefe5049d9(o==null ? e==null : o.equals(e))d98ca7951c814b9263d12f482df06c69,
     * if this set contains such an element.  Returns 78f983dbc27872ba42409adefe5049d9trued98ca7951c814b9263d12f482df06c69 if
     * this set contained the element (or equivalently, if this set
     * changed as a result of the call).  (This set will not contain the
     * element once the call returns.)
     *
     * @param o object to be removed from this set, if present
     * @return 78f983dbc27872ba42409adefe5049d9trued98ca7951c814b9263d12f482df06c69 if the set contained the specified element
     */
    //删除对象
    public boolean remove(Object o) {
        return map.remove(o)==PRESENT;
    }

    /**
     * Removes all of the elements from this set.
     * The set will be empty after this call returns.
     */
    //清空set
    public void clear() {
        map.clear();
    }

    /**
     * Returns a shallow copy of this 78f983dbc27872ba42409adefe5049d9HashSetd98ca7951c814b9263d12f482df06c69 instance: the elements
     * themselves are not cloned.
     *
     * @return a shallow copy of this set
     */
    //深拷贝
    @SuppressWarnings("unchecked")
    public Object clone() {
        try {
            HashSet1a4db2c2c2313771e5742b6debf617a1 newSet = (HashSet1a4db2c2c2313771e5742b6debf617a1) super.clone();
            newSet.map = (HashMap8e751a6654859f4ad3ab548dad16afed) map.clone();
            return newSet;
        } catch (CloneNotSupportedException e) {
            throw new InternalError(e);
        }
    }

    /**
     * Save the state of this 78f983dbc27872ba42409adefe5049d9HashSetd98ca7951c814b9263d12f482df06c69 instance to a stream (that is,
     * serialize it).
     *
     * @serialData The capacity of the backing 78f983dbc27872ba42409adefe5049d9HashMapd98ca7951c814b9263d12f482df06c69 instance
     *             (int), and its load factor (float) are emitted, followed by
     *             the size of the set (the number of elements it contains)
     *             (int), followed by all of its elements (each an Object) in
     *             no particular order.
     */
    //序列化写
    private void writeObject(java.io.ObjectOutputStream s)
            throws java.io.IOException {
        // Write out any hidden serialization magic
        s.defaultWriteObject();

        // Write out HashMap capacity and load factor
        s.writeInt(map.capacity());
        s.writeFloat(map.loadFactor());

        // Write out size
        s.writeInt(map.size());

        // Write out all elements in the proper order.
        for (E e : map.keySet())
            s.writeObject(e);
    }

    /**
     * Reconstitute the 78f983dbc27872ba42409adefe5049d9HashSetd98ca7951c814b9263d12f482df06c69 instance from a stream (that is,
     * deserialize it).
     */
    //序列化读
    private void readObject(java.io.ObjectInputStream s)
            throws java.io.IOException, ClassNotFoundException {
        // Read in any hidden serialization magic
        s.defaultReadObject();

        // Read capacity and verify non-negative.
        int capacity = s.readInt();
        if (capacity d4fe061c272c30507d0f695857f4f355)this) instanceof LinkedHashSet ?
                new LinkedHashMapc81ac021d9fe376b0afca3578d66e836(capacity, loadFactor) :
                new HashMapc81ac021d9fe376b0afca3578d66e836(capacity, loadFactor));

        // Read in all elements in the proper order.
        for (int i=0; ia999b12ce7dfa09cdfcdb48cd9e1e64e47bdf838fe1f241804499a8943350a02late-binding5db79b134e9f6b82c0b36e0489ee08edd1c6776b927dc33c5d9114750b586338
     * and 907fae80ddef53131f3292ee4f81644bfail-fastd1c6776b927dc33c5d9114750b586338 {@link Spliterator} over the elements in this
     * set.
     *
     * e388a4556c0f65e1904146cc1a846beeThe {@code Spliterator} reports {@link Spliterator#SIZED} and
     * {@link Spliterator#DISTINCT}.  Overriding implementations should document
     * the reporting of additional characteristic values.
     *
     * @return a {@code Spliterator} over the elements in this set
     * @since 1.8
     */
    public Spliterator1a4db2c2c2313771e5742b6debf617a1 spliterator() {
        return new HashMap.KeySpliteratorc81ac021d9fe376b0afca3578d66e836(map, 0, -1, 0, 0);
    }
}

The above is the detailed content of Detailed introduction to Java collection HashSet. For more information, please follow other related articles on the PHP Chinese website!

Statement:
The content of this article is voluntarily contributed by netizens, and the copyright belongs to the original author. This site does not assume corresponding legal responsibility. If you find any content suspected of plagiarism or infringement, please contact admin@php.cn