ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/jsr166/jsr166/src/main/java/util/TreeSet.java
Revision: 1.20
Committed: Tue Feb 7 20:54:24 2006 UTC (18 years, 3 months ago) by jsr166
Branch: MAIN
Changes since 1.19: +0 -1 lines
Log Message:
6378729: Remove workaround for 6280605

File Contents

# User Rev Content
1 dl 1.1 /*
2     * %W% %E%
3     *
4 jsr166 1.19 * Copyright 2006 Sun Microsystems, Inc. All rights reserved.
5 dl 1.1 * SUN PROPRIETARY/CONFIDENTIAL. Use is subject to license terms.
6     */
7    
8 jsr166 1.8 package java.util;
9 dl 1.1
10     /**
11 jsr166 1.11 * A {@link NavigableSet} implementation based on a {@link TreeMap}.
12     * The elements are ordered using their {@linkplain Comparable natural
13     * ordering}, or by a {@link Comparator} provided at set creation
14     * time, depending on which constructor is used.
15 dl 1.1 *
16 jsr166 1.11 * <p>This implementation provides guaranteed log(n) time cost for the basic
17     * operations (<tt>add</tt>, <tt>remove</tt> and <tt>contains</tt>).
18 dl 1.1 *
19 jsr166 1.11 * <p>Note that the ordering maintained by a set (whether or not an explicit
20 dl 1.1 * comparator is provided) must be <i>consistent with equals</i> if it is to
21     * correctly implement the <tt>Set</tt> interface. (See <tt>Comparable</tt>
22     * or <tt>Comparator</tt> for a precise definition of <i>consistent with
23     * equals</i>.) This is so because the <tt>Set</tt> interface is defined in
24     * terms of the <tt>equals</tt> operation, but a <tt>TreeSet</tt> instance
25 jsr166 1.11 * performs all element comparisons using its <tt>compareTo</tt> (or
26     * <tt>compare</tt>) method, so two elements that are deemed equal by this method
27 dl 1.1 * are, from the standpoint of the set, equal. The behavior of a set
28     * <i>is</i> well-defined even if its ordering is inconsistent with equals; it
29 jsr166 1.11 * just fails to obey the general contract of the <tt>Set</tt> interface.
30 dl 1.1 *
31 jsr166 1.18 * <p><strong>Note that this implementation is not synchronized.</strong>
32     * If multiple threads access a tree set concurrently, and at least one
33     * of the threads modifies the set, it <i>must</i> be synchronized
34     * externally. This is typically accomplished by synchronizing on some
35     * object that naturally encapsulates the set.
36     * If no such object exists, the set should be "wrapped" using the
37     * {@link Collections#synchronizedSortedSet Collections.synchronizedSortedSet}
38     * method. This is best done at creation time, to prevent accidental
39     * unsynchronized access to the set: <pre>
40     * SortedSet s = Collections.synchronizedSortedSet(new TreeSet(...));</pre>
41 dl 1.1 *
42 jsr166 1.11 * <p>The iterators returned by this class's <tt>iterator</tt> method are
43 dl 1.1 * <i>fail-fast</i>: if the set is modified at any time after the iterator is
44     * created, in any way except through the iterator's own <tt>remove</tt>
45 jsr166 1.11 * method, the iterator will throw a {@link ConcurrentModificationException}.
46 dl 1.1 * Thus, in the face of concurrent modification, the iterator fails quickly
47     * and cleanly, rather than risking arbitrary, non-deterministic behavior at
48     * an undetermined time in the future.
49     *
50     * <p>Note that the fail-fast behavior of an iterator cannot be guaranteed
51     * as it is, generally speaking, impossible to make any hard guarantees in the
52     * presence of unsynchronized concurrent modification. Fail-fast iterators
53     * throw <tt>ConcurrentModificationException</tt> on a best-effort basis.
54     * Therefore, it would be wrong to write a program that depended on this
55     * exception for its correctness: <i>the fail-fast behavior of iterators
56 jsr166 1.10 * should be used only to detect bugs.</i>
57 dl 1.1 *
58 jsr166 1.10 * <p>This class is a member of the
59 dl 1.1 * <a href="{@docRoot}/../guide/collections/index.html">
60     * Java Collections Framework</a>.
61     *
62 jsr166 1.11 * @param <E> the type of elements maintained by this set
63     *
64 dl 1.1 * @author Josh Bloch
65     * @version %I%, %G%
66     * @see Collection
67     * @see Set
68     * @see HashSet
69     * @see Comparable
70     * @see Comparator
71     * @see TreeMap
72     * @since 1.2
73     */
74    
75     public class TreeSet<E>
76     extends AbstractSet<E>
77     implements NavigableSet<E>, Cloneable, java.io.Serializable
78     {
79     private transient NavigableMap<E,Object> m; // The backing Map
80    
81     // Dummy value to associate with an Object in the backing Map
82     private static final Object PRESENT = new Object();
83    
84     /**
85 jsr166 1.11 * Constructs a set backed by the specified navigable map.
86 dl 1.1 */
87     private TreeSet(NavigableMap<E,Object> m) {
88     this.m = m;
89     }
90    
91     /**
92 jsr166 1.11 * Constructs a new, empty tree set, sorted according to the
93     * natural ordering of its elements. All elements inserted into
94     * the set must implement the {@link Comparable} interface.
95     * Furthermore, all such elements must be <i>mutually
96     * comparable</i>: <tt>e1.compareTo(e2)</tt> must not throw a
97 dl 1.1 * <tt>ClassCastException</tt> for any elements <tt>e1</tt> and
98 jsr166 1.11 * <tt>e2</tt> in the set. If the user attempts to add an element
99     * to the set that violates this constraint (for example, the user
100     * attempts to add a string element to a set whose elements are
101     * integers), the <tt>add(Object)</tt> call will throw a
102     * <tt>ClassCastException</tt>.
103 dl 1.1 */
104     public TreeSet() {
105     this(new TreeMap<E,Object>());
106     }
107    
108     /**
109 jsr166 1.12 * Constructs a new, empty tree set, sorted according to the specified
110     * comparator. All elements inserted into the set must be <i>mutually
111     * comparable</i> by the specified comparator: <tt>comparator.compare(e1,
112     * e2)</tt> must not throw a <tt>ClassCastException</tt> for any elements
113     * <tt>e1</tt> and <tt>e2</tt> in the set. If the user attempts to add
114     * an element to the set that violates this constraint, the
115     * <tt>add(Object)</tt> call will throw a <tt>ClassCastException</tt>.
116 jsr166 1.11 *
117     * @param comparator the comparator that will be used to order this set.
118     * If <tt>null</tt>, the {@linkplain Comparable natural
119     * ordering} of the elements will be used.
120     */
121     public TreeSet(Comparator<? super E> comparator) {
122     this(new TreeMap<E,Object>(comparator));
123 dl 1.1 }
124    
125     /**
126 jsr166 1.12 * Constructs a new tree set containing the elements in the specified
127     * collection, sorted according to the <i>natural ordering</i> of its
128     * elements. All elements inserted into the set must implement the
129     * {@link Comparable} interface. Furthermore, all such elements must be
130     * <i>mutually comparable</i>: <tt>e1.compareTo(e2)</tt> must not throw a
131 jsr166 1.11 * <tt>ClassCastException</tt> for any elements <tt>e1</tt> and
132     * <tt>e2</tt> in the set.
133     *
134     * @param c collection whose elements will comprise the new set
135     * @throws ClassCastException if the elements in <tt>c</tt> are
136     * not {@link Comparable}, or are not mutually comparable
137     * @throws NullPointerException if the specified collection is null
138 dl 1.1 */
139     public TreeSet(Collection<? extends E> c) {
140     this();
141     addAll(c);
142     }
143    
144     /**
145 jsr166 1.11 * Constructs a new tree set containing the same elements and
146     * using the same ordering as the specified sorted set.
147 dl 1.1 *
148 jsr166 1.11 * @param s sorted set whose elements will comprise the new set
149     * @throws NullPointerException if the specified sorted set is null
150 dl 1.1 */
151     public TreeSet(SortedSet<E> s) {
152     this(s.comparator());
153     addAll(s);
154     }
155    
156     /**
157 jsr166 1.13 * Returns an iterator over the elements in this set in ascending order.
158 dl 1.1 *
159 jsr166 1.13 * @return an iterator over the elements in this set in ascending order
160 dl 1.1 */
161     public Iterator<E> iterator() {
162 jsr166 1.11 return m.keySet().iterator();
163 dl 1.1 }
164    
165     /**
166 jsr166 1.13 * Returns an iterator over the elements in this set in descending order.
167 dl 1.1 *
168 jsr166 1.13 * @return an iterator over the elements in this set in descending order
169 jsr166 1.17 * @since 1.6
170 dl 1.1 */
171     public Iterator<E> descendingIterator() {
172     return m.descendingKeySet().iterator();
173     }
174    
175     /**
176     * Returns the number of elements in this set (its cardinality).
177     *
178 jsr166 1.11 * @return the number of elements in this set (its cardinality)
179 dl 1.1 */
180     public int size() {
181     return m.size();
182     }
183    
184     /**
185     * Returns <tt>true</tt> if this set contains no elements.
186     *
187 jsr166 1.11 * @return <tt>true</tt> if this set contains no elements
188 dl 1.1 */
189     public boolean isEmpty() {
190     return m.isEmpty();
191     }
192    
193     /**
194     * Returns <tt>true</tt> if this set contains the specified element.
195 jsr166 1.16 * More formally, returns <tt>true</tt> if and only if this set
196     * contains an element <tt>e</tt> such that
197     * <tt>(o==null&nbsp;?&nbsp;e==null&nbsp;:&nbsp;o.equals(e))</tt>.
198 dl 1.1 *
199 jsr166 1.16 * @param o object to be checked for containment in this set
200 jsr166 1.11 * @return <tt>true</tt> if this set contains the specified element
201 dl 1.1 * @throws ClassCastException if the specified object cannot be compared
202 jsr166 1.11 * with the elements currently in the set
203 jsr166 1.15 * @throws NullPointerException if the specified element is null
204     * and this set uses natural ordering, or its comparator
205     * does not permit null elements
206 dl 1.1 */
207     public boolean contains(Object o) {
208     return m.containsKey(o);
209     }
210    
211     /**
212     * Adds the specified element to this set if it is not already present.
213 jsr166 1.16 * More formally, adds the specified element <tt>e</tt> to this set if
214     * the set contains no element <tt>e2</tt> such that
215     * <tt>(e==null&nbsp;?&nbsp;e2==null&nbsp;:&nbsp;e.equals(e2))</tt>.
216     * If this set already contains the element, the call leaves the set
217     * unchanged and returns <tt>false</tt>.
218 dl 1.1 *
219 jsr166 1.11 * @param e element to be added to this set
220 jsr166 1.16 * @return <tt>true</tt> if this set did not already contain the specified
221 jsr166 1.11 * element
222 dl 1.1 * @throws ClassCastException if the specified object cannot be compared
223 jsr166 1.16 * with the elements currently in this set
224 jsr166 1.15 * @throws NullPointerException if the specified element is null
225     * and this set uses natural ordering, or its comparator
226     * does not permit null elements
227 dl 1.1 */
228 jsr166 1.7 public boolean add(E e) {
229     return m.put(e, PRESENT)==null;
230 dl 1.1 }
231    
232     /**
233     * Removes the specified element from this set if it is present.
234 jsr166 1.16 * More formally, removes an element <tt>e</tt> such that
235     * <tt>(o==null&nbsp;?&nbsp;e==null&nbsp;:&nbsp;o.equals(e))</tt>,
236     * if this set contains such an element. Returns <tt>true</tt> if
237     * this set contained the element (or equivalently, if this set
238     * changed as a result of the call). (This set will not contain the
239     * element once the call returns.)
240 dl 1.1 *
241 jsr166 1.11 * @param o object to be removed from this set, if present
242 jsr166 1.16 * @return <tt>true</tt> if this set contained the specified element
243 dl 1.1 * @throws ClassCastException if the specified object cannot be compared
244 jsr166 1.16 * with the elements currently in this set
245 jsr166 1.15 * @throws NullPointerException if the specified element is null
246     * and this set uses natural ordering, or its comparator
247     * does not permit null elements
248 dl 1.1 */
249     public boolean remove(Object o) {
250     return m.remove(o)==PRESENT;
251     }
252    
253     /**
254     * Removes all of the elements from this set.
255 jsr166 1.11 * The set will be empty after this call returns.
256 dl 1.1 */
257     public void clear() {
258     m.clear();
259     }
260    
261     /**
262     * Adds all of the elements in the specified collection to this set.
263     *
264 jsr166 1.14 * @param c collection containing elements to be added to this set
265 jsr166 1.11 * @return <tt>true</tt> if this set changed as a result of the call
266 dl 1.1 * @throws ClassCastException if the elements provided cannot be compared
267 jsr166 1.11 * with the elements currently in the set
268     * @throws NullPointerException if the specified collection is null or
269     * if any element is null and this set uses natural ordering, or
270     * its comparator does not permit null elements
271 dl 1.1 */
272     public boolean addAll(Collection<? extends E> c) {
273     // Use linear-time version if applicable
274     if (m.size()==0 && c.size() > 0 &&
275     c instanceof SortedSet &&
276     m instanceof TreeMap) {
277 jsr166 1.9 SortedSet<? extends E> set = (SortedSet<? extends E>) c;
278 dl 1.1 TreeMap<E,Object> map = (TreeMap<E, Object>) m;
279 jsr166 1.9 Comparator<? super E> cc = (Comparator<? super E>) set.comparator();
280 dl 1.1 Comparator<? super E> mc = map.comparator();
281     if (cc==mc || (cc != null && cc.equals(mc))) {
282     map.addAllForTreeSet(set, PRESENT);
283     return true;
284     }
285     }
286     return super.addAll(c);
287     }
288    
289     /**
290 jsr166 1.11 * @throws ClassCastException {@inheritDoc}
291 dl 1.1 * @throws NullPointerException if <tt>fromElement</tt> or
292 jsr166 1.11 * <tt>toElement</tt> is null and this set uses natural ordering,
293     * or its comparator does not permit null elements
294     * @throws IllegalArgumentException {@inheritDoc}
295 jsr166 1.17 * @since 1.6
296 dl 1.1 */
297 dl 1.3 public NavigableSet<E> navigableSubSet(E fromElement, E toElement) {
298     return new TreeSet<E>(m.navigableSubMap(fromElement, toElement));
299 dl 1.1 }
300    
301     /**
302 jsr166 1.11 * @throws ClassCastException {@inheritDoc}
303     * @throws NullPointerException if <tt>toElement</tt> is null and
304     * this set uses natural ordering, or its comparator does
305     * not permit null elements
306     * @throws IllegalArgumentException {@inheritDoc}
307 jsr166 1.17 * @since 1.6
308 dl 1.1 */
309 dl 1.3 public NavigableSet<E> navigableHeadSet(E toElement) {
310     return new TreeSet<E>(m.navigableHeadMap(toElement));
311 dl 1.1 }
312    
313     /**
314 jsr166 1.11 * @throws ClassCastException {@inheritDoc}
315     * @throws NullPointerException if <tt>fromElement</tt> is null and
316     * this set uses natural ordering, or its comparator does
317     * not permit null elements
318     * @throws IllegalArgumentException {@inheritDoc}
319 jsr166 1.17 * @since 1.6
320 dl 1.1 */
321 dl 1.3 public NavigableSet<E> navigableTailSet(E fromElement) {
322     return new TreeSet<E>(m.navigableTailMap(fromElement));
323     }
324    
325     /**
326 jsr166 1.11 * Equivalent to {@link #navigableSubSet} but with a return type
327     * conforming to the <tt>SortedSet</tt> interface.
328     *
329     * <p>{@inheritDoc}
330     *
331     * @throws ClassCastException {@inheritDoc}
332 dl 1.3 * @throws NullPointerException if <tt>fromElement</tt> or
333 jsr166 1.11 * <tt>toElement</tt> is null and this set uses natural ordering,
334     * or its comparator does not permit null elements
335     * @throws IllegalArgumentException {@inheritDoc}
336 dl 1.3 */
337     public SortedSet<E> subSet(E fromElement, E toElement) {
338     return new TreeSet<E>(m.navigableSubMap(fromElement, toElement));
339     }
340    
341     /**
342 jsr166 1.11 * Equivalent to {@link #navigableHeadSet} but with a return type
343     * conforming to the <tt>SortedSet</tt> interface.
344     *
345     * <p>{@inheritDoc}
346 dl 1.3 *
347 jsr166 1.11 * @throws ClassCastException {@inheritDoc}
348     * @throws NullPointerException if <tt>toElement</tt> is null
349     * and this set uses natural ordering, or its comparator does
350     * not permit null elements
351     * @throws IllegalArgumentException {@inheritDoc}
352 dl 1.3 */
353     public SortedSet<E> headSet(E toElement) {
354     return new TreeSet<E>(m.navigableHeadMap(toElement));
355     }
356    
357     /**
358 jsr166 1.11 * Equivalent to {@link #navigableTailSet} but with a return type
359     * conforming to the <tt>SortedSet</tt> interface.
360     *
361     * <p>{@inheritDoc}
362     *
363     * @throws ClassCastException {@inheritDoc}
364     * @throws NullPointerException if <tt>fromElement</tt> is null
365     * and this set uses natural ordering, or its comparator does
366     * not permit null elements
367     * @throws IllegalArgumentException {@inheritDoc}
368 dl 1.3 */
369     public SortedSet<E> tailSet(E fromElement) {
370     return new TreeSet<E>(m.navigableTailMap(fromElement));
371 dl 1.1 }
372    
373     public Comparator<? super E> comparator() {
374     return m.comparator();
375     }
376    
377     /**
378 jsr166 1.11 * @throws NoSuchElementException {@inheritDoc}
379 dl 1.1 */
380     public E first() {
381     return m.firstKey();
382     }
383    
384     /**
385 jsr166 1.11 * @throws NoSuchElementException {@inheritDoc}
386 dl 1.1 */
387     public E last() {
388     return m.lastKey();
389     }
390    
391     // NavigableSet API methods
392    
393     /**
394 jsr166 1.11 * @throws ClassCastException {@inheritDoc}
395 jsr166 1.15 * @throws NullPointerException if the specified element is null
396     * and this set uses natural ordering, or its comparator
397     * does not permit null elements
398 jsr166 1.17 * @since 1.6
399 dl 1.1 */
400 jsr166 1.11 public E lower(E e) {
401     return m.lowerKey(e);
402 dl 1.1 }
403    
404     /**
405 jsr166 1.11 * @throws ClassCastException {@inheritDoc}
406 jsr166 1.15 * @throws NullPointerException if the specified element is null
407     * and this set uses natural ordering, or its comparator
408     * does not permit null elements
409 jsr166 1.17 * @since 1.6
410 dl 1.1 */
411 jsr166 1.11 public E floor(E e) {
412     return m.floorKey(e);
413 dl 1.1 }
414    
415     /**
416 jsr166 1.11 * @throws ClassCastException {@inheritDoc}
417 jsr166 1.15 * @throws NullPointerException if the specified element is null
418     * and this set uses natural ordering, or its comparator
419     * does not permit null elements
420 jsr166 1.17 * @since 1.6
421 dl 1.1 */
422 jsr166 1.11 public E ceiling(E e) {
423     return m.ceilingKey(e);
424 dl 1.1 }
425    
426     /**
427 jsr166 1.11 * @throws ClassCastException {@inheritDoc}
428 jsr166 1.15 * @throws NullPointerException if the specified element is null
429     * and this set uses natural ordering, or its comparator
430     * does not permit null elements
431 jsr166 1.17 * @since 1.6
432 dl 1.1 */
433 jsr166 1.7 public E higher(E e) {
434     return m.higherKey(e);
435 dl 1.1 }
436    
437 jsr166 1.17 /**
438     * @since 1.6
439     */
440 dl 1.1 public E pollFirst() {
441     Map.Entry<E,?> e = m.pollFirstEntry();
442     return (e == null)? null : e.getKey();
443     }
444    
445 jsr166 1.17 /**
446     * @since 1.6
447     */
448 dl 1.1 public E pollLast() {
449     Map.Entry<E,?> e = m.pollLastEntry();
450     return (e == null)? null : e.getKey();
451     }
452    
453     /**
454     * Returns a shallow copy of this <tt>TreeSet</tt> instance. (The elements
455     * themselves are not cloned.)
456     *
457 jsr166 1.11 * @return a shallow copy of this set
458 dl 1.1 */
459     public Object clone() {
460     TreeSet<E> clone = null;
461     try {
462     clone = (TreeSet<E>) super.clone();
463     } catch (CloneNotSupportedException e) {
464     throw new InternalError();
465     }
466    
467     clone.m = new TreeMap<E,Object>(m);
468    
469     return clone;
470     }
471    
472     /**
473     * Save the state of the <tt>TreeSet</tt> instance to a stream (that is,
474     * serialize it).
475     *
476     * @serialData Emits the comparator used to order this set, or
477 jsr166 1.11 * <tt>null</tt> if it obeys its elements' natural ordering
478     * (Object), followed by the size of the set (the number of
479     * elements it contains) (int), followed by all of its
480     * elements (each an Object) in order (as determined by the
481     * set's Comparator, or by the elements' natural ordering if
482 dl 1.1 * the set has no Comparator).
483     */
484     private void writeObject(java.io.ObjectOutputStream s)
485     throws java.io.IOException {
486     // Write out any hidden stuff
487     s.defaultWriteObject();
488    
489     // Write out Comparator
490     s.writeObject(m.comparator());
491    
492     // Write out size
493     s.writeInt(m.size());
494    
495     // Write out all elements in the proper order.
496     for (Iterator i=m.keySet().iterator(); i.hasNext(); )
497     s.writeObject(i.next());
498     }
499    
500     /**
501     * Reconstitute the <tt>TreeSet</tt> instance from a stream (that is,
502     * deserialize it).
503     */
504     private void readObject(java.io.ObjectInputStream s)
505     throws java.io.IOException, ClassNotFoundException {
506     // Read in any hidden stuff
507     s.defaultReadObject();
508    
509     // Read in Comparator
510 jsr166 1.9 Comparator<? super E> c = (Comparator<? super E>) s.readObject();
511 dl 1.1
512     // Create backing TreeMap
513     TreeMap<E,Object> tm;
514     if (c==null)
515     tm = new TreeMap<E,Object>();
516     else
517     tm = new TreeMap<E,Object>(c);
518     m = tm;
519    
520     // Read in size
521     int size = s.readInt();
522    
523     tm.readTreeSet(size, s, PRESENT);
524     }
525    
526     private static final long serialVersionUID = -2479143000061671589L;
527     }