自各儿动手写写:HashSet、LinkedHashSet源码浅析
自己动手写写:HashSet、LinkedHashSet源码浅析
这篇文章我只是作为一个简要的分析。
首先可以看看之前写的两篇的博文,只要你熟悉了下面这两个类的源码就显得很简单了!
自己动手写写:HashMap源码浅析
自己动手写写:LinkedHashMap源码浅析
先来介绍下HashSet吧!
public class HashSet<E> extends AbstractSet<E> implements Set<E>, Cloneable, java.io.Serializable
一个不包含重复元素的 collection。更正式地说,set 不包含满足 e1.equals(e2) 的元素对 e1 和 e2,并且最多包含一个 null 元素。
通过Set接口的描述可以看得出来Set内部是不能有重复元素的,而HashSet的内部是通过维护一个HashMap来实现的,即放入HashSet的value值均作为HashMap的key值来存储的,这样就可以保证了不重复性,并且HashSet拥有HashMap中响应的某些特性!
接下来看LinkedHashSet
public class LinkedHashSet<E> extends HashSet<E> implements Set<E>, Cloneable, java.io.Serializable
LinkedHashSet是HashSet的一个子类,它与HashSet的不同在于:
具有可预知迭代顺序的 Set 接口的哈希表和链接列表实现。此实现与 HashSet 的不同之外在于,后者维护着一个运行于所有条目的双重链接列表。 此链接列表定义了迭代顺序,即按照将元素插入到 set 中的顺序(插入顺序)进行迭代。注意,插入顺序不 受在 set 中重新插入的 元素的影响。 (如果在 s.contains(e) 返回 true 后立即调用 s.add(e),则元素 e 会被重新插入到 set s 中。)
我们看一下HashSet的一个构造函数:
/** * 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 */ HashSet(int initialCapacity, float loadFactor, boolean dummy) { map = new LinkedHashMap<E, Object>(initialCapacity, loadFactor); }
此构造函数的访问权限是default,即同包下可见!LinkedHashSet就是通过此构造函数,通过维护这一个LinkedHashMap来实现的。