集合(一)Set:HashSet,TreeSet

集合(一)Set:HashSet,TreeSet

参考:https://mp.weixin.qq.com/s/ZTNJIbrDfLUdkEU5aiDRFQ

Set是不允许出现重复的集合,主要有HashSet和TreeSet两大类,判断重复元素时,会用到HashCode()和equals()方法。

HashSet使用HashMap的key存储元素,计算元素的hash值来获取元素在集合中的位置,

TreeSet是红黑树结构,每一个元素都是树中的节点,插入的元素都是进行排序

1.HashSet

HashSet基于HashMap,底层是通过HashMap的API来实现的。是哈希表结构。

1)允许null值

2)无序

3)非线程安全

key是新增的元素,value是一个固定的值。

它继承于AbstractSet,实现了Set, Cloneable, Serializable接口。

HashSet中的两个变量:

map:存储元素的地方,是一个HashMap,当有元素要插入到HashSet中,会被当成map的key保存到map属性中去

present:每个key对应的vaule默认为PRESENT,也就是new了一个对象

hashSet的构造方法:初始化map属性,new了一个HashMap对象

add()添加方法,底层调用hashmap的put()方法

源码:

如果了解了HashMap的实现原理,那下面的代码很容易理解,先计算hash值,如果相同,则调用equals(), == 进行判断,若相同则覆盖原来的元素,不相同的时候才向map中添加元素。

public V put(K key, V value) {
    if (table == EMPTY_TABLE) {
        inflateTable(threshold);
    }
    if (key == null)
        return putForNullKey(value);
    int hash = hash(key);
    int i = indexFor(hash, table.length);
    for (Entry<K,V> e = table[i]; e != null; e = e.next) {
        Object k;
        if (e.hash == hash && ((k = e.key) == key || key.equals(k))) {
            V oldValue = e.value;
            e.value = value;
            e.recordAccess(this);
            return oldValue;
        }
    }
    modCount++;
    addEntry(hash, key, value, i);
    return null;
}

2.TreeSet

底层通过TreeMap来实现,具有排序功能(自然排序(默认)和自定义排序)

它继承AbstractSet,实现NavigableSet(搜索功能), Cloneable(克隆), Serializable(序列化,可用hessian协议来传输)接口。

1)有序

2)允许null值

3)底层红黑树结构

4)元素不允许重复

5)非线程安全

TreeSet的add()方法:底层调用TreeMap的put()方法,put()方法里面会调用到compare(key ,key)方法,进行key大小的比较。因此TreeSet的类型如果是自定义的类型,就必须重写compareTo()方法或者实现Comparator接口重写compare()方法,说明比较的是类中的哪个属性才行,不然会报错

猜你喜欢

转载自blog.csdn.net/weixin_38108266/article/details/82355578