java中HashSet和TreeSet的区别
1.Set
Set继承于Collection接口,是一个不允许出现重复元素,并且无序的集合,主要有HashSet和TreeSet两大实现类。
在判断重复元素的时候,Set集合会调用hashCode()和equal()方法来实现。
HashSet是哈希表结构,主要利用HashMap的key来存储元素,计算插入元素的hashCode来获取元素在集合中的位置;
TreeSet是红黑树结构,每一个元素都是树中的一个节点,插入的元素都会进行排序;
Set集合框架结构:

1.1 HashSet
1. 底层数据结构是哈希表(是一个元素为链表的数组)
2. HashSet其实是用HashMap()来实现的,HashMap()是Map接口的实现类。
调用HashSet的add()方法其实就是调用HashMap()中的put()
Hashset具有如下特点:
-
不允许出现重复因素;
-
允许插入Null值;
-
元素无序(添加顺序和遍历顺序不一致);
-
线程不安全,若2个线程同时操作HashSet,必须通过代码实现同步;
1.2 TreeSet
1. 底层数据结构是红黑树(是一个自平衡的二叉树)

- TreeSet是一个有序的集合,基于TreeMap实现,支持两种排序方式:自然排序和定制排序。
- TreeSet是非同步的,线程不安全的。
a:自然排序(元素具备比较性)
让元素所属的类实现Comparable接口,重写其中的compareTo方法
package cn.itcast_03; public class Student implements Comparable<Student>{ private String name; private int age; public Student() { super(); // TODO Auto-generated constructor stub } public Student(String name, int age) { super(); this.name = name; this.age = age; } public String getName() { return name; } public void setName(String name) { this.name = name; } public int getAge() { return age; } public void setAge(int age) { this.age = age; } @Override public int compareTo(Student s) { int num = 0; num = this.age - s.age; int num2 = num == 0 ? this.name.compareTo(s.name) : num; return num2; } }
b:定制排序(比较器排序,集合具备比较性)
让集合构造方法接收Comparator的实现类对象,在实现类中重写compare()方法
这种方法通过调用集合的带参构造来实现比较
public TreeSet(Comperator comparator)//比较器排序
Comperator 是一个接口,把接口作为参数其实就是需要这个接口的实现类的对象
通过API我们可以得知这个接口中方法的格式,另外,这种需要一个接口的实现类的对象作为参数的情况,开发中我们常常使用匿名内部类的格式
TreeSet<Student> ts = new TreeSet<Student>(new Comparator<Student>() { public int compare(Student s1,Student s2) { //注意这个三目比较,赋值的优先级最小,==最大,三目中间 int num = s1.getName().length() - s2.getName().length(); int num2 = num == 0 ? s1.getName().compareTo(s2.getName()) : num; int num3 = num2 == 0 ? s1.getAge() - s2.getAge() : num2; return num3; } });
TreeSet具有如下特点:
-
对插入的元素进行排序,是一个有序的集合(主要与HashSet的区别);
-
底层使用红黑树结构,而不是哈希表结构;
-
允许插入Null值;
-
不允许插入重复元素;
-
线程不安全;
1.3 LinkHashSet( HashSet+LinkedHashMap )
对于 LinkedHashSet 而言,它继承与 HashSet、又基于 LinkedHashMap 来实现的。LinkedHashSet 底层使用 LinkedHashMap 来保存所有元素,它继承与 HashSet,其所有的方法操作上又与 HashSet 相同,因此LinkedHashSet 的实现上非常简单,只提供了四个构造方法,并通过传递一个标识参数,调用父类的构造器,底层构造一个 LinkedHashMap 来实现,在相关操作上与父类 HashSet 的操作相同,直接调用父类 HashSet 的方法即可。
总结:
- 底层数据结构是链表和哈希表。(FIFO插入有序,唯一)
- 由链表保证元素有序
- 由哈希表保证元素唯一

浙公网安备 33010602011771号