TreeSet源码解析

这一章,我们对TreeSet进行学习。
我们先对TreeSet有个整体认识,然后再学习它的源码,最后再通过实例来学会使用TreeSet。

第1部分 TreeSet介绍

TreeSet简介

TreeSet 是一个有序的集合,它的作用是提供有序的Set集合。它继承于AbstractSet抽象类,实现了NavigableSet<E>, Cloneable, java.io.Serializable接口。
TreeSet 继承于AbstractSet,所以它是一个Set集合,具有Set的属性和方法。
TreeSet 实现了NavigableSet接口,意味着它支持一系列的导航方法。比如查找与指定目标最匹配项。
TreeSet 实现了Cloneable接口,意味着它能被克隆。
TreeSet 实现了java.io.Serializable接口,意味着它支持序列化。

TreeSet是基于TreeMap实现的。TreeSet中的元素支持2种排序方式:自然排序 或者 根据创建TreeSet 时提供的 Comparator 进行排序。这取决于使用的构造方法。
TreeSet为基本操作(add、remove 和 contains)提供受保证的 log(n) 时间开销。
另外,TreeSet是非同步的。 它的iterator 方法返回的迭代器是fail-fast的。


TreeSet的继承关系

双击代码全选
1
2
3
4
5
6
7
java.lang.Object
    ↳     java.util.AbstractCollection<E>
          ↳     java.util.AbstractSet<E>
                ↳     java.util.TreeSet<E>
      
public class TreeSet<E> extends AbstractSet<E>       
     implements NavigableSet<E>, Cloneable, java.io.Serializable{}

TreeSet与Collection关系如下图:

TreeSet的构造函数

双击代码全选
1
2
3
4
5
6
7
8
9
10
11
// 默认构造函数。使用该构造函数,TreeSet中的元素按照自然排序进行排列。
TreeSet()
      
// 创建的TreeSet包含collection
TreeSet(Collection<? extends E> collection)
      
// 指定TreeSet的比较器
TreeSet(Comparator<? super E> comparator)
      
// 创建的TreeSet包含set
TreeSet(SortedSet<E> set)

TreeSet的API

双击代码全选
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
boolean                   add(E object)
boolean                   addAll(Collection<? extends E> collection)
void                      clear()
Object                    clone()
boolean                   contains(Object object)
E                         first()
boolean                   isEmpty()
E                         last()
E                         pollFirst()
E                         pollLast()
E                         lower(E e)
E                         floor(E e)
E                         ceiling(E e)
E                         higher(E e)
boolean                   remove(Object object)
int                       size()
Comparator<? super E>     comparator()
Iterator<E>               iterator()
Iterator<E>               descendingIterator()
SortedSet<E>              headSet(E end)
NavigableSet<E>           descendingSet()
NavigableSet<E>           headSet(E end, boolean endInclusive)
SortedSet<E>              subSet(E start, E end)
NavigableSet<E>           subSet(E start, boolean startInclusive, E end, boolean endInclusive)
NavigableSet<E>           tailSet(E start, boolean startInclusive)
SortedSet<E>              tailSet(E start)

说明:

(01) TreeSet是有序的Set集合,因此支持add、remove、get等方法。
(02) 和NavigableSet一样,TreeSet的导航方法大致可以区分为两类,一类时提供元素项的导航方法,返回某个元素;另一类时提供集合的导航方法,返回某个集合。
lower、floor、ceiling 和 higher 分别返回小于、小于等于、大于等于、大于给定元素的元素,如果不存在这样的元素,则返回 null。



第2部分 TreeSet源码解析

为了更了解TreeSet的原理,下面对TreeSet源码代码作出分析。

双击代码全选
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
package java.util;
      
public class TreeSet<E> extends AbstractSet<E>
     implements NavigableSet<E>, Cloneable, java.io.Serializable
{
     // NavigableMap对象
     private transient NavigableMap<E,Object> m;
      
     // TreeSet是通过TreeMap实现的,
     // PRESENT是键-值对中的值。
     private static final Object PRESENT = new Object();
      
     // 不带参数的构造函数。创建一个空的TreeMap
     public TreeSet() {
         this ( new TreeMap<E,Object>());
     }
      
     // 将TreeMap赋值给 "NavigableMap对象m"
     TreeSet(NavigableMap<E,Object> m) {
         this .m = m;
     }
      
     // 带比较器的构造函数。
     public TreeSet(Comparator<? super E> comparator) {
         this ( new TreeMap<E,Object>(comparator));
     }
      
     // 创建TreeSet,并将集合c中的全部元素都添加到TreeSet中
     public TreeSet(Collection<? extends E> c) {
         this ();
         // 将集合c中的元素全部添加到TreeSet中
         addAll(c);
     }
      
     // 创建TreeSet,并将s中的全部元素都添加到TreeSet中
     public TreeSet(SortedSet<E> s) {
         this (s.comparator());
         addAll(s);
     }
      
     // 返回TreeSet的顺序排列的迭代器。
     // 因为TreeSet时TreeMap实现的,所以这里实际上时返回TreeMap的“键集”对应的迭代器
     public Iterator<E> iterator() {
         return m.navigableKeySet().iterator();
     }
      
     // 返回TreeSet的逆序排列的迭代器。
     // 因为TreeSet时TreeMap实现的,所以这里实际上时返回TreeMap的“键集”对应的迭代器
     public Iterator<E> descendingIterator() {
         return m.descendingKeySet().iterator();
     }
      
     // 返回TreeSet的大小
     public int size() {
         return m.size();
     }
      
     // 返回TreeSet是否为空
     public boolean isEmpty() {
         return m.isEmpty();
     }
      
     // 返回TreeSet是否包含对象(o)
     public boolean contains(Object o) {
         return m.containsKey(o);
     }
      
     // 添加e到TreeSet中
     public boolean add(E e) {
         return m.put(e, PRESENT)== null ;
     }
      
     // 删除TreeSet中的对象o
     public boolean remove(Object o) {
         return m.remove(o)==PRESENT;
     }
      
     // 清空TreeSet
     public void clear() {
         m.clear();
     }
      
     // 将集合c中的全部元素添加到TreeSet中
     public  boolean addAll(Collection<? extends E> c) {
         // Use linear-time version if applicable
         if (m.size()== 0 && c.size() > 0 &&
             c instanceof SortedSet &&
             m instanceof TreeMap) {
             SortedSet<? extends E> set = (SortedSet<? extends E>) c;
             TreeMap<E,Object> map = (TreeMap<E, Object>) m;
             Comparator<? super E> cc = (Comparator<? super E>) set.comparator();
             Comparator<? super E> mc = map.comparator();
             if (cc==mc || (cc != null && cc.equals(mc))) {
                 map.addAllForTreeSet(set, PRESENT);
                 return true ;
             }
         }
         return super .addAll(c);
     }
      
     // 返回子Set,实际上是通过TreeMap的subMap()实现的。
     public NavigableSet<E> subSet(E fromElement, boolean fromInclusive,
                                   E toElement,   boolean toInclusive) {
         return new TreeSet<E>(m.subMap(fromElement, fromInclusive,
                                        toElement,   toInclusive));
     }
      
     // 返回Set的头部,范围是:从头部到toElement。
     // inclusive是是否包含toElement的标志
     public NavigableSet<E> headSet(E toElement, boolean inclusive) {
         return new TreeSet<E>(m.headMap(toElement, inclusive));
     }
      
     // 返回Set的尾部,范围是:从fromElement到结尾。
     // inclusive是是否包含fromElement的标志
     public NavigableSet<E> tailSet(E fromElement, boolean inclusive) {
         return new TreeSet<E>(m.tailMap(fromElement, inclusive));
     }
      
     // 返回子Set。范围是:从fromElement(包括)到toElement(不包括)。
     public SortedSet<E> subSet(E fromElement, E toElement) {
         return subSet(fromElement, true , toElement, false );
     }
      
     // 返回Set的头部,范围是:从头部到toElement(不包括)。
     public SortedSet<E> headSet(E toElement) {
         return headSet(toElement, false );
     }
      
     // 返回Set的尾部,范围是:从fromElement到结尾(不包括)。
     public SortedSet<E> tailSet(E fromElement) {
         return tailSet(fromElement, true );
     }
      
     // 返回Set的比较器
     public Comparator<? super E> comparator() {
         return m.comparator();
     }
      
     // 返回Set的第一个元素
     public E first() {
         return m.firstKey();
     }
      
     // 返回Set的最后一个元素
     public E first() {
     public E last() {
         return m.lastKey();
     }
      
     // 返回Set中小于e的最大元素
     public E lower(E e) {
         return m.lowerKey(e);
     }
      
     // 返回Set中小于/等于e的最大元素
     public E floor(E e) {
         return m.floorKey(e);
     }
      
     // 返回Set中大于/等于e的最小元素
     public E ceiling(E e) {
         return m.ceilingKey(e);
     }
      
     // 返回Set中大于e的最小元素
     public E higher(E e) {
         return m.higherKey(e);
     }
      
     // 获取第一个元素,并将该元素从TreeMap中删除。
     public E pollFirst() {
         Map.Entry<E,?> e = m.pollFirstEntry();
         return (e == null )? null : e.getKey();
     }
      
     // 获取最后一个元素,并将该元素从TreeMap中删除。
     public E pollLast() {
         Map.Entry<E,?> e = m.pollLastEntry();
         return (e == null )? null : e.getKey();
     }
      
     // 克隆一个TreeSet,并返回Object对象
     public Object clone() {
         TreeSet<E> clone = null ;
         try {
             clone = (TreeSet<E>) super .clone();
         } catch (CloneNotSupportedException e) {
             throw new InternalError();
         }
      
         clone.m = new TreeMap<E,Object>(m);
         return clone;
     }
      
     // java.io.Serializable的写入函数
     // 将TreeSet的“比较器、容量,所有的元素值”都写入到输出流中
     private void writeObject(java.io.ObjectOutputStream s)
         throws java.io.IOException {
         s.defaultWriteObject();
      
         // 写入比较器
         s.writeObject(m.comparator());
      
         // 写入容量
         s.writeInt(m.size());
      
         // 写入“TreeSet中的每一个元素”
         for (Iterator i=m.keySet().iterator(); i.hasNext(); )
             s.writeObject(i.next());
     }
      
     // java.io.Serializable的读取函数:根据写入方式读出
     // 先将TreeSet的“比较器、容量、所有的元素值”依次读出
     private void readObject(java.io.ObjectInputStream s)
         throws java.io.IOException, ClassNotFoundException {
         // Read in any hidden stuff
         s.defaultReadObject();
      
         // 从输入流中读取TreeSet的“比较器”
         Comparator<? super E> c = (Comparator<? super E>) s.readObject();
      
         TreeMap<E,Object> tm;
         if (c== null )
             tm = new TreeMap<E,Object>();
         else
             tm = new TreeMap<E,Object>(c);
         m = tm;
      
         // 从输入流中读取TreeSet的“容量”
         int size = s.readInt();
      
         // 从输入流中读取TreeSet的“全部元素”
         tm.readTreeSet(size, s, PRESENT);
     }
      
     // TreeSet的序列版本号
     private static final long serialVersionUID = -2479143000061671589L;
}

来源: cnblogs   作者:如果天空不死   
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值