🚀 优质资源分享 🚀
HashSet 类图
![Hash类图](https://i-blog.csdnimg.cn/blog_migrate/22837bfb2a142d8ae3531b2813550858.png)
HashSet 简单说明
HashSet
实现了 Set
接口
HashSet
底层实际上是由 HashMap
实现的
public HashSet() {
map = new HashMap<>();
}
- 可以存放
null
,但是只能有一个 null
HashSet
不保证元素是有序的(即不保证存放元素的顺序和取出元素的顺序一致),取决于 hash
后,再确定索引的结果
- 不能有重复的元素
HashSet 底层机制说明
HashSet
底层是 HashMap
,HashMap
底层是 数组 + 链表 + 红黑树
模拟数组+链表的结构
![模拟数组+链表的结构](https://i-blog.csdnimg.cn/blog_migrate/37e71d5ae24af0ec5c139c143d2fbd4c.png)
/**
* 模拟 HashSet 数组+链表的结构
*/
public class HashSetStructureMain {
public static void main(String[] args) {
// 模拟一个 HashSet(HashMap) 的底层结构
// 1. 创建一个数组,数组的类型为 Node[]
// 2. 有些地方直接把 Node[] 数组称为 表
Node[] table = new Node[16];
System.out.println(table);
// 3. 创建节点
Node john = new Node("john", null);
table[2] = jhon; // 把节点 john 放在数组索引为 2 的位置
Node jack = new Node("jack", null);
jhon.next = jack; // 将 jack 挂载到 jhon 的后面
Node rose = new Node("rose", null);
jack.next = rose; // 将 rose 挂载到 jack 的后面
Node lucy = new Node("lucy", null);
table[3] = lucy; // 将 lucy 放在数组索引为 3 的位置
System.out.println(table);
}
}
// 节点类 存储数据,可以指向下一个节点,从而形成链表
class Node{
Object item; // 存放数据
Node next; // 指向下一个节点
public Node(Object item, Node next){
this.item = item;
this.next = next;
}
}
HashSet 添加元素底层机制
HashSet 添加元素的底层实现
HashSet
底层是 HashMap
- 当添加一个元素时,会先得到 待添加元素的
hash
值,然后将其转换成一个 索引值
- 查询存储数据表(Node 数组)
table
,看当前 待添加元素 所对应的 索引值 的位置是否已经存放了 其它元素
- 如果当前 索引值 所对应的的位置不存在 其它元素,就将当前 待添加元素 放到这个 索引值 所对应的的位置