ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/jsr166/jsr166/src/main/java/util/TreeMap.java
Revision: 1.17
Committed: Thu May 26 12:07:07 2005 UTC (18 years, 11 months ago) by dl
Branch: MAIN
Changes since 1.16: +5 -5 lines
Log Message:
Avoid some generics cast warnings

File Contents

# User Rev Content
1 dl 1.1 /*
2     * %W% %E%
3     *
4 jsr166 1.10 * Copyright 2005 Sun Microsystems, Inc. All rights reserved.
5 dl 1.1 * SUN PROPRIETARY/CONFIDENTIAL. Use is subject to license terms.
6     */
7    
8 dl 1.8 package java.util;
9 dl 1.1
10     /**
11 jsr166 1.14 * A Red-Black tree based {@link NavigableMap} implementation.
12     * The map is sorted according to the {@linkplain Comparable natural
13     * ordering} of its keys, or by a {@link Comparator} provided at map
14     * creation time, depending on which constructor is used.
15 dl 1.1 *
16 jsr166 1.14 * <p>This implementation provides guaranteed log(n) time cost for the
17 dl 1.1 * <tt>containsKey</tt>, <tt>get</tt>, <tt>put</tt> and <tt>remove</tt>
18     * operations. Algorithms are adaptations of those in Cormen, Leiserson, and
19 jsr166 1.14 * Rivest's <I>Introduction to Algorithms</I>.
20 dl 1.1 *
21 jsr166 1.14 * <p>Note that the ordering maintained by a sorted map (whether or not an
22 dl 1.1 * explicit comparator is provided) must be <i>consistent with equals</i> if
23     * this sorted map is to correctly implement the <tt>Map</tt> interface. (See
24     * <tt>Comparable</tt> or <tt>Comparator</tt> for a precise definition of
25     * <i>consistent with equals</i>.) This is so because the <tt>Map</tt>
26     * interface is defined in terms of the equals operation, but a map performs
27     * all key comparisons using its <tt>compareTo</tt> (or <tt>compare</tt>)
28     * method, so two keys that are deemed equal by this method are, from the
29     * standpoint of the sorted map, equal. The behavior of a sorted map
30     * <i>is</i> well-defined even if its ordering is inconsistent with equals; it
31 jsr166 1.14 * just fails to obey the general contract of the <tt>Map</tt> interface.
32 dl 1.1 *
33 jsr166 1.14 * <p><b>Note that this implementation is not synchronized.</b> If multiple
34 dl 1.1 * threads access a map concurrently, and at least one of the threads modifies
35     * the map structurally, it <i>must</i> be synchronized externally. (A
36     * structural modification is any operation that adds or deletes one or more
37     * mappings; merely changing the value associated with an existing key is not
38     * a structural modification.) This is typically accomplished by
39     * synchronizing on some object that naturally encapsulates the map. If no
40     * such object exists, the map should be "wrapped" using the
41     * <tt>Collections.synchronizedMap</tt> method. This is best done at creation
42     * time, to prevent accidental unsynchronized access to the map:
43     * <pre>
44     * Map m = Collections.synchronizedMap(new TreeMap(...));
45 jsr166 1.14 * </pre>
46 dl 1.1 *
47 jsr166 1.14 * <p>The iterators returned by the <tt>iterator</tt> method of the collections
48     * returned by all of this class's "collection view methods" are
49 dl 1.1 * <i>fail-fast</i>: if the map is structurally modified at any time after the
50     * iterator is created, in any way except through the iterator's own
51 jsr166 1.14 * <tt>remove</tt> method, the iterator will throw a {@link
52     * ConcurrentModificationException}. Thus, in the face of concurrent
53 dl 1.1 * modification, the iterator fails quickly and cleanly, rather than risking
54 jsr166 1.14 * arbitrary, non-deterministic behavior at an undetermined time in the future.
55 dl 1.1 *
56     * <p>Note that the fail-fast behavior of an iterator cannot be guaranteed
57     * as it is, generally speaking, impossible to make any hard guarantees in the
58     * presence of unsynchronized concurrent modification. Fail-fast iterators
59     * throw <tt>ConcurrentModificationException</tt> on a best-effort basis.
60     * Therefore, it would be wrong to write a program that depended on this
61     * exception for its correctness: <i>the fail-fast behavior of iterators
62 dl 1.5 * should be used only to detect bugs.</i>
63 dl 1.1 *
64     * <p>All <tt>Map.Entry</tt> pairs returned by methods in this class
65     * and its views represent snapshots of mappings at the time they were
66     * produced. They do <em>not</em> support the <tt>Entry.setValue</tt>
67     * method. (Note however that it is possible to change mappings in the
68     * associated map using <tt>put</tt>.)
69     *
70     * <p>This class is a member of the
71     * <a href="{@docRoot}/../guide/collections/index.html">
72     * Java Collections Framework</a>.
73     *
74 jsr166 1.14 * @param <K> the type of keys maintained by this map
75     * @param <V> the type of mapped values
76     *
77 dl 1.1 * @author Josh Bloch and Doug Lea
78     * @version %I%, %G%
79     * @see Map
80     * @see HashMap
81     * @see Hashtable
82     * @see Comparable
83     * @see Comparator
84     * @see Collection
85     * @see Collections#synchronizedMap(Map)
86     * @since 1.2
87     */
88    
89     public class TreeMap<K,V>
90     extends AbstractMap<K,V>
91     implements NavigableMap<K,V>, Cloneable, java.io.Serializable
92     {
93     /**
94 jsr166 1.14 * The comparator used to maintain order in this tree map, or
95     * null if it uses the natural ordering of its keys.
96 dl 1.1 *
97     * @serial
98     */
99     private Comparator<? super K> comparator = null;
100    
101     private transient Entry<K,V> root = null;
102    
103     /**
104     * The number of entries in the tree
105     */
106     private transient int size = 0;
107    
108     /**
109     * The number of structural modifications to the tree.
110     */
111     private transient int modCount = 0;
112    
113     private void incrementSize() { modCount++; size++; }
114     private void decrementSize() { modCount++; size--; }
115    
116     /**
117 jsr166 1.14 * Constructs a new, empty tree map, using the natural ordering of its
118     * keys. All keys inserted into the map must implement the {@link
119     * Comparable} interface. Furthermore, all such keys must be
120     * <i>mutually comparable</i>: <tt>k1.compareTo(k2)</tt> must not throw
121     * a <tt>ClassCastException</tt> for any keys <tt>k1</tt> and
122     * <tt>k2</tt> in the map. If the user attempts to put a key into the
123     * map that violates this constraint (for example, the user attempts to
124     * put a string key into a map whose keys are integers), the
125     * <tt>put(Object key, Object value)</tt> call will throw a
126     * <tt>ClassCastException</tt>.
127 dl 1.1 */
128     public TreeMap() {
129     }
130    
131     /**
132 jsr166 1.14 * Constructs a new, empty tree map, ordered according to the given
133     * comparator. All keys inserted into the map must be <i>mutually
134     * comparable</i> by the given comparator: <tt>comparator.compare(k1,
135     * k2)</tt> must not throw a <tt>ClassCastException</tt> for any keys
136     * <tt>k1</tt> and <tt>k2</tt> in the map. If the user attempts to put
137     * a key into the map that violates this constraint, the <tt>put(Object
138     * key, Object value)</tt> call will throw a
139     * <tt>ClassCastException</tt>.
140     *
141     * @param comparator the comparator that will be used to order this map.
142     * If <tt>null</tt>, the {@linkplain Comparable natural
143     * ordering} of the keys will be used.
144     */
145     public TreeMap(Comparator<? super K> comparator) {
146     this.comparator = comparator;
147 dl 1.1 }
148    
149     /**
150 jsr166 1.14 * Constructs a new tree map containing the same mappings as the given
151     * map, ordered according to the <i>natural ordering</i> of its keys.
152     * All keys inserted into the new map must implement the {@link
153     * Comparable} interface. Furthermore, all such keys must be
154     * <i>mutually comparable</i>: <tt>k1.compareTo(k2)</tt> must not throw
155     * a <tt>ClassCastException</tt> for any keys <tt>k1</tt> and
156     * <tt>k2</tt> in the map. This method runs in n*log(n) time.
157     *
158     * @param m the map whose mappings are to be placed in this map
159     * @throws ClassCastException if the keys in m are not {@link Comparable},
160     * or are not mutually comparable
161     * @throws NullPointerException if the specified map is null
162 dl 1.1 */
163     public TreeMap(Map<? extends K, ? extends V> m) {
164     putAll(m);
165     }
166    
167     /**
168 jsr166 1.14 * Constructs a new tree map containing the same mappings and
169     * using the same ordering as the specified sorted map. This
170     * method runs in linear time.
171 dl 1.1 *
172     * @param m the sorted map whose mappings are to be placed in this map,
173 jsr166 1.14 * and whose comparator is to be used to sort this map
174     * @throws NullPointerException if the specified map is null
175 dl 1.1 */
176     public TreeMap(SortedMap<K, ? extends V> m) {
177     comparator = m.comparator();
178     try {
179     buildFromSorted(m.size(), m.entrySet().iterator(), null, null);
180     } catch (java.io.IOException cannotHappen) {
181     } catch (ClassNotFoundException cannotHappen) {
182     }
183     }
184    
185    
186     // Query Operations
187    
188     /**
189     * Returns the number of key-value mappings in this map.
190     *
191 jsr166 1.14 * @return the number of key-value mappings in this map
192 dl 1.1 */
193     public int size() {
194     return size;
195     }
196    
197     /**
198     * Returns <tt>true</tt> if this map contains a mapping for the specified
199     * key.
200     *
201 jsr166 1.14 * @param key key whose presence in this map is to be tested
202 dl 1.1 * @return <tt>true</tt> if this map contains a mapping for the
203 jsr166 1.14 * specified key
204     * @throws ClassCastException if the specified key cannot be compared
205     * with the keys currently in the map
206     * @throws NullPointerException if the specified key is null
207     * and this map uses natural ordering, or its comparator
208     * does not permit null keys
209 dl 1.1 */
210     public boolean containsKey(Object key) {
211     return getEntry(key) != null;
212     }
213    
214     /**
215     * Returns <tt>true</tt> if this map maps one or more keys to the
216     * specified value. More formally, returns <tt>true</tt> if and only if
217     * this map contains at least one mapping to a value <tt>v</tt> such
218     * that <tt>(value==null ? v==null : value.equals(v))</tt>. This
219 jsr166 1.14 * operation requires time linear in the map size.
220 dl 1.1 *
221 jsr166 1.14 * @param value value whose presence in this map is to be tested
222     * @return <tt>true</tt> if a mapping to <tt>value</tt> exists;
223     * <tt>false</tt> otherwise
224 dl 1.1 * @since 1.2
225     */
226     public boolean containsValue(Object value) {
227     return (root==null ? false :
228     (value==null ? valueSearchNull(root)
229     : valueSearchNonNull(root, value)));
230     }
231    
232     private boolean valueSearchNull(Entry n) {
233     if (n.value == null)
234     return true;
235    
236     // Check left and right subtrees for value
237     return (n.left != null && valueSearchNull(n.left)) ||
238     (n.right != null && valueSearchNull(n.right));
239     }
240    
241     private boolean valueSearchNonNull(Entry n, Object value) {
242     // Check this node for the value
243     if (value.equals(n.value))
244     return true;
245    
246     // Check left and right subtrees for value
247     return (n.left != null && valueSearchNonNull(n.left, value)) ||
248     (n.right != null && valueSearchNonNull(n.right, value));
249     }
250    
251     /**
252 jsr166 1.14 * Returns the value to which this map maps the specified key, or
253     * <tt>null</tt> if the map contains no mapping for the key. A return
254 dl 1.1 * value of <tt>null</tt> does not <i>necessarily</i> indicate that the
255     * map contains no mapping for the key; it's also possible that the map
256 jsr166 1.14 * explicitly maps the key to <tt>null</tt>. The {@link #containsKey}
257 dl 1.1 * operation may be used to distinguish these two cases.
258     *
259 jsr166 1.14 * @param key key whose associated value is to be returned
260 dl 1.1 * @return the value to which this map maps the specified key, or
261 jsr166 1.14 * <tt>null</tt> if the map contains no mapping for the key
262     * @throws ClassCastException if the specified key cannot be compared
263     * with the keys currently in the map
264     * @throws NullPointerException if the specified key is null
265     * and this map uses natural ordering, or its comparator
266     * does not permit null keys
267 dl 1.1 */
268     public V get(Object key) {
269     Entry<K,V> p = getEntry(key);
270     return (p==null ? null : p.value);
271     }
272    
273     public Comparator<? super K> comparator() {
274     return comparator;
275     }
276    
277     /**
278 jsr166 1.14 * @throws NoSuchElementException {@inheritDoc}
279 dl 1.1 */
280     public K firstKey() {
281     return key(getFirstEntry());
282     }
283    
284     /**
285 jsr166 1.14 * @throws NoSuchElementException {@inheritDoc}
286 dl 1.1 */
287     public K lastKey() {
288     return key(getLastEntry());
289     }
290    
291     /**
292 jsr166 1.14 * Copies all of the mappings from the specified map to this map.
293     * These mappings replace any mappings that this map had for any
294     * of the keys currently in the specified map.
295     *
296     * @param map mappings to be stored in this map
297     * @throws ClassCastException if the class of a key or value in
298     * the specified map prevents it from being stored in this map
299     * @throws NullPointerException if the specified map is null or
300     * the specified map contains a null key and this map does not
301     * permit null keys
302 dl 1.1 */
303     public void putAll(Map<? extends K, ? extends V> map) {
304     int mapSize = map.size();
305     if (size==0 && mapSize!=0 && map instanceof SortedMap) {
306     Comparator c = ((SortedMap)map).comparator();
307     if (c == comparator || (c != null && c.equals(comparator))) {
308     ++modCount;
309     try {
310     buildFromSorted(mapSize, map.entrySet().iterator(),
311     null, null);
312     } catch (java.io.IOException cannotHappen) {
313     } catch (ClassNotFoundException cannotHappen) {
314     }
315     return;
316     }
317     }
318     super.putAll(map);
319     }
320    
321     /**
322     * Returns this map's entry for the given key, or <tt>null</tt> if the map
323     * does not contain an entry for the key.
324     *
325     * @return this map's entry for the given key, or <tt>null</tt> if the map
326 jsr166 1.14 * does not contain an entry for the key
327     * @throws ClassCastException if the specified key cannot be compared
328     * with the keys currently in the map
329     * @throws NullPointerException if the specified key is null
330     * and this map uses natural ordering, or its comparator
331     * does not permit null keys
332 dl 1.1 */
333     private Entry<K,V> getEntry(Object key) {
334     // Offload comparator-based version for sake of performance
335     if (comparator != null)
336     return getEntryUsingComparator(key);
337 jsr166 1.12 Comparable<? super K> k = (Comparable<? super K>) key;
338 dl 1.1 Entry<K,V> p = root;
339     while (p != null) {
340     int cmp = k.compareTo(p.key);
341     if (cmp < 0)
342     p = p.left;
343     else if (cmp > 0)
344     p = p.right;
345     else
346     return p;
347     }
348     return null;
349     }
350    
351     /**
352     * Version of getEntry using comparator. Split off from getEntry
353     * for performance. (This is not worth doing for most methods,
354     * that are less dependent on comparator performance, but is
355     * worthwhile here.)
356     */
357     private Entry<K,V> getEntryUsingComparator(Object key) {
358     K k = (K) key;
359     Comparator<? super K> cpr = comparator;
360     Entry<K,V> p = root;
361     while (p != null) {
362     int cmp = cpr.compare(k, p.key);
363     if (cmp < 0)
364     p = p.left;
365     else if (cmp > 0)
366     p = p.right;
367     else
368     return p;
369     }
370     return null;
371     }
372    
373     /**
374     * Gets the entry corresponding to the specified key; if no such entry
375     * exists, returns the entry for the least key greater than the specified
376     * key; if no such entry exists (i.e., the greatest key in the Tree is less
377     * than the specified key), returns <tt>null</tt>.
378     */
379     private Entry<K,V> getCeilingEntry(K key) {
380     Entry<K,V> p = root;
381     if (p==null)
382     return null;
383    
384     while (true) {
385     int cmp = compare(key, p.key);
386     if (cmp < 0) {
387     if (p.left != null)
388     p = p.left;
389     else
390     return p;
391     } else if (cmp > 0) {
392     if (p.right != null) {
393     p = p.right;
394     } else {
395     Entry<K,V> parent = p.parent;
396     Entry<K,V> ch = p;
397     while (parent != null && ch == parent.right) {
398     ch = parent;
399     parent = parent.parent;
400     }
401     return parent;
402     }
403     } else
404     return p;
405     }
406     }
407    
408     /**
409     * Gets the entry corresponding to the specified key; if no such entry
410     * exists, returns the entry for the greatest key less than the specified
411     * key; if no such entry exists, returns <tt>null</tt>.
412     */
413     private Entry<K,V> getFloorEntry(K key) {
414     Entry<K,V> p = root;
415     if (p==null)
416     return null;
417    
418     while (true) {
419     int cmp = compare(key, p.key);
420     if (cmp > 0) {
421     if (p.right != null)
422     p = p.right;
423     else
424     return p;
425     } else if (cmp < 0) {
426     if (p.left != null) {
427     p = p.left;
428     } else {
429     Entry<K,V> parent = p.parent;
430     Entry<K,V> ch = p;
431     while (parent != null && ch == parent.left) {
432     ch = parent;
433     parent = parent.parent;
434     }
435     return parent;
436     }
437     } else
438     return p;
439    
440     }
441     }
442    
443     /**
444     * Gets the entry for the least key greater than the specified
445     * key; if no such entry exists, returns the entry for the least
446     * key greater than the specified key; if no such entry exists
447     * returns <tt>null</tt>.
448     */
449     private Entry<K,V> getHigherEntry(K key) {
450     Entry<K,V> p = root;
451     if (p==null)
452     return null;
453    
454     while (true) {
455     int cmp = compare(key, p.key);
456     if (cmp < 0) {
457     if (p.left != null)
458     p = p.left;
459     else
460     return p;
461     } else {
462     if (p.right != null) {
463     p = p.right;
464     } else {
465     Entry<K,V> parent = p.parent;
466     Entry<K,V> ch = p;
467     while (parent != null && ch == parent.right) {
468     ch = parent;
469     parent = parent.parent;
470     }
471     return parent;
472     }
473     }
474     }
475     }
476    
477     /**
478     * Returns the entry for the greatest key less than the specified key; if
479     * no such entry exists (i.e., the least key in the Tree is greater than
480     * the specified key), returns <tt>null</tt>.
481     */
482     private Entry<K,V> getLowerEntry(K key) {
483     Entry<K,V> p = root;
484     if (p==null)
485     return null;
486    
487     while (true) {
488     int cmp = compare(key, p.key);
489     if (cmp > 0) {
490     if (p.right != null)
491     p = p.right;
492     else
493     return p;
494     } else {
495     if (p.left != null) {
496     p = p.left;
497     } else {
498     Entry<K,V> parent = p.parent;
499     Entry<K,V> ch = p;
500     while (parent != null && ch == parent.left) {
501     ch = parent;
502     parent = parent.parent;
503     }
504     return parent;
505     }
506     }
507     }
508     }
509    
510     /**
511 jsr166 1.14 * Returns the key corresponding to the specified Entry.
512     * @throws NoSuchElementException if the Entry is null
513 dl 1.1 */
514     private static <K> K key(Entry<K,?> e) {
515     if (e==null)
516     throw new NoSuchElementException();
517     return e.key;
518     }
519    
520     /**
521     * Associates the specified value with the specified key in this map.
522     * If the map previously contained a mapping for this key, the old
523     * value is replaced.
524     *
525 jsr166 1.14 * @param key key with which the specified value is to be associated
526     * @param value value to be associated with the specified key
527 dl 1.1 *
528 jsr166 1.14 * @return the previous value associated with <tt>key</tt>, or
529     * <tt>null</tt> if there was no mapping for <tt>key</tt>.
530     * (A <tt>null</tt> return can also indicate that the map
531     * previously associated <tt>null</tt> with <tt>key</tt>.)
532     * @throws ClassCastException if the specified key cannot be compared
533     * with the keys currently in the map
534     * @throws NullPointerException if the specified key is null
535     * and this map uses natural ordering, or its comparator
536     * does not permit null keys
537 dl 1.1 */
538     public V put(K key, V value) {
539     Entry<K,V> t = root;
540    
541     if (t == null) {
542 dl 1.13 if (key == null) {
543     if (comparator == null)
544     throw new NullPointerException();
545     comparator.compare(key, key);
546     }
547 dl 1.1 incrementSize();
548     root = new Entry<K,V>(key, value, null);
549     return null;
550 dl 1.8 }
551 dl 1.1
552     while (true) {
553     int cmp = compare(key, t.key);
554     if (cmp == 0) {
555     return t.setValue(value);
556     } else if (cmp < 0) {
557     if (t.left != null) {
558     t = t.left;
559     } else {
560     incrementSize();
561     t.left = new Entry<K,V>(key, value, t);
562     fixAfterInsertion(t.left);
563     return null;
564     }
565     } else { // cmp > 0
566     if (t.right != null) {
567     t = t.right;
568     } else {
569     incrementSize();
570     t.right = new Entry<K,V>(key, value, t);
571     fixAfterInsertion(t.right);
572     return null;
573     }
574     }
575     }
576     }
577    
578     /**
579     * Removes the mapping for this key from this TreeMap if present.
580     *
581     * @param key key for which mapping should be removed
582 jsr166 1.14 * @return the previous value associated with <tt>key</tt>, or
583     * <tt>null</tt> if there was no mapping for <tt>key</tt>.
584     * (A <tt>null</tt> return can also indicate that the map
585     * previously associated <tt>null</tt> with <tt>key</tt>.)
586     * @throws ClassCastException if the specified key cannot be compared
587     * with the keys currently in the map
588     * @throws NullPointerException if the specified key is null
589     * and this map uses natural ordering, or its comparator
590     * does not permit null keys
591 dl 1.1 */
592     public V remove(Object key) {
593     Entry<K,V> p = getEntry(key);
594     if (p == null)
595     return null;
596    
597     V oldValue = p.value;
598     deleteEntry(p);
599     return oldValue;
600     }
601    
602     /**
603 jsr166 1.14 * Removes all of the mappings from this map.
604     * The map will be empty after this call returns.
605 dl 1.1 */
606     public void clear() {
607     modCount++;
608     size = 0;
609     root = null;
610     }
611    
612     /**
613     * Returns a shallow copy of this <tt>TreeMap</tt> instance. (The keys and
614     * values themselves are not cloned.)
615     *
616 jsr166 1.14 * @return a shallow copy of this map
617 dl 1.1 */
618     public Object clone() {
619     TreeMap<K,V> clone = null;
620     try {
621     clone = (TreeMap<K,V>) super.clone();
622     } catch (CloneNotSupportedException e) {
623     throw new InternalError();
624     }
625    
626     // Put clone into "virgin" state (except for comparator)
627     clone.root = null;
628     clone.size = 0;
629     clone.modCount = 0;
630     clone.entrySet = null;
631     clone.descendingEntrySet = null;
632     clone.descendingKeySet = null;
633    
634     // Initialize clone with our mappings
635     try {
636     clone.buildFromSorted(size, entrySet().iterator(), null, null);
637     } catch (java.io.IOException cannotHappen) {
638     } catch (ClassNotFoundException cannotHappen) {
639     }
640    
641     return clone;
642     }
643    
644     // NavigableMap API methods
645    
646     public Map.Entry<K,V> firstEntry() {
647     Entry<K,V> e = getFirstEntry();
648 dl 1.16 return (e == null)? null : new AbstractMap.SimpleImmutableEntry<K,V>(e);
649 dl 1.1 }
650    
651     public Map.Entry<K,V> lastEntry() {
652     Entry<K,V> e = getLastEntry();
653 dl 1.16 return (e == null)? null : new AbstractMap.SimpleImmutableEntry<K,V>(e);
654 dl 1.1 }
655    
656     public Map.Entry<K,V> pollFirstEntry() {
657     Entry<K,V> p = getFirstEntry();
658 dl 1.8 if (p == null)
659 dl 1.1 return null;
660 dl 1.16 Map.Entry<K,V> result = new AbstractMap.SimpleImmutableEntry<K,V>(p);
661 dl 1.1 deleteEntry(p);
662     return result;
663     }
664    
665     public Map.Entry<K,V> pollLastEntry() {
666     Entry<K,V> p = getLastEntry();
667 dl 1.8 if (p == null)
668 dl 1.1 return null;
669 dl 1.16 Map.Entry<K,V> result = new AbstractMap.SimpleImmutableEntry<K,V>(p);
670 dl 1.1 deleteEntry(p);
671     return result;
672     }
673    
674     /**
675 jsr166 1.14 * @throws ClassCastException {@inheritDoc}
676     * @throws NullPointerException if the specified key is null
677     * and this map uses natural ordering, or its comparator
678     * does not permit null keys
679 dl 1.1 */
680 jsr166 1.14 public Map.Entry<K,V> lowerEntry(K key) {
681     Entry<K,V> e = getLowerEntry(key);
682 dl 1.16 return (e == null)? null : new AbstractMap.SimpleImmutableEntry<K,V>(e);
683 dl 1.1 }
684    
685     /**
686 jsr166 1.14 * @throws ClassCastException {@inheritDoc}
687     * @throws NullPointerException if the specified key is null
688     * and this map uses natural ordering, or its comparator
689     * does not permit null keys
690 dl 1.1 */
691 jsr166 1.14 public K lowerKey(K key) {
692     Entry<K,V> e = getLowerEntry(key);
693 dl 1.1 return (e == null)? null : e.key;
694     }
695    
696     /**
697 jsr166 1.14 * @throws ClassCastException {@inheritDoc}
698     * @throws NullPointerException if the specified key is null
699     * and this map uses natural ordering, or its comparator
700     * does not permit null keys
701 dl 1.1 */
702     public Map.Entry<K,V> floorEntry(K key) {
703     Entry<K,V> e = getFloorEntry(key);
704 dl 1.16 return (e == null)? null : new AbstractMap.SimpleImmutableEntry<K,V>(e);
705 dl 1.1 }
706    
707     /**
708 jsr166 1.14 * @throws ClassCastException {@inheritDoc}
709     * @throws NullPointerException if the specified key is null
710     * and this map uses natural ordering, or its comparator
711     * does not permit null keys
712 dl 1.1 */
713     public K floorKey(K key) {
714     Entry<K,V> e = getFloorEntry(key);
715     return (e == null)? null : e.key;
716     }
717    
718     /**
719 jsr166 1.14 * @throws ClassCastException {@inheritDoc}
720     * @throws NullPointerException if the specified key is null
721     * and this map uses natural ordering, or its comparator
722     * does not permit null keys
723 dl 1.1 */
724 jsr166 1.14 public Map.Entry<K,V> ceilingEntry(K key) {
725     Entry<K,V> e = getCeilingEntry(key);
726 dl 1.16 return (e == null)? null : new AbstractMap.SimpleImmutableEntry<K,V>(e);
727 dl 1.1 }
728    
729     /**
730 jsr166 1.14 * @throws ClassCastException {@inheritDoc}
731     * @throws NullPointerException if the specified key is null
732     * and this map uses natural ordering, or its comparator
733     * does not permit null keys
734 dl 1.1 */
735 jsr166 1.14 public K ceilingKey(K key) {
736     Entry<K,V> e = getCeilingEntry(key);
737 dl 1.1 return (e == null)? null : e.key;
738     }
739    
740     /**
741 jsr166 1.14 * @throws ClassCastException {@inheritDoc}
742     * @throws NullPointerException if the specified key is null
743     * and this map uses natural ordering, or its comparator
744     * does not permit null keys
745 dl 1.1 */
746 jsr166 1.14 public Map.Entry<K,V> higherEntry(K key) {
747     Entry<K,V> e = getHigherEntry(key);
748 dl 1.16 return (e == null)? null : new AbstractMap.SimpleImmutableEntry<K,V>(e);
749 dl 1.1 }
750    
751     /**
752 jsr166 1.14 * @throws ClassCastException {@inheritDoc}
753     * @throws NullPointerException if the specified key is null
754     * and this map uses natural ordering, or its comparator
755     * does not permit null keys
756 dl 1.1 */
757 jsr166 1.14 public K higherKey(K key) {
758     Entry<K,V> e = getHigherEntry(key);
759 dl 1.1 return (e == null)? null : e.key;
760     }
761    
762     // Views
763    
764     /**
765     * Fields initialized to contain an instance of the entry set view
766     * the first time this view is requested. Views are stateless, so
767     * there's no reason to create more than one.
768     */
769     private transient Set<Map.Entry<K,V>> entrySet = null;
770     private transient Set<Map.Entry<K,V>> descendingEntrySet = null;
771 dl 1.8 private transient Set<K> descendingKeySet = null;
772 dl 1.1
773     /**
774 jsr166 1.14 * Returns a {@link Set} view of the keys contained in this map.
775     * The set's iterator returns the keys in ascending order.
776     * The set is backed by the map, so changes to the map are
777     * reflected in the set, and vice-versa. If the map is modified
778     * while an iteration over the set is in progress (except through
779     * the iterator's own <tt>remove</tt> operation), the results of
780     * the iteration are undefined. The set supports element removal,
781     * which removes the corresponding mapping from the map, via the
782     * <tt>Iterator.remove</tt>, <tt>Set.remove</tt>,
783 jsr166 1.15 * <tt>removeAll</tt>, <tt>retainAll</tt>, and <tt>clear</tt>
784     * operations. It does not support the <tt>add</tt> or <tt>addAll</tt>
785 jsr166 1.14 * operations.
786 dl 1.1 */
787     public Set<K> keySet() {
788     Set<K> ks = keySet;
789     return (ks != null) ? ks : (keySet = new KeySet());
790     }
791    
792     class KeySet extends AbstractSet<K> {
793     public Iterator<K> iterator() {
794     return new KeyIterator(getFirstEntry());
795     }
796 dl 1.8
797 dl 1.1 public int size() {
798     return TreeMap.this.size();
799     }
800 dl 1.8
801 dl 1.1 public boolean contains(Object o) {
802     return containsKey(o);
803     }
804 dl 1.8
805 dl 1.1 public boolean remove(Object o) {
806     int oldSize = size;
807     TreeMap.this.remove(o);
808     return size != oldSize;
809     }
810 dl 1.8
811 dl 1.1 public void clear() {
812     TreeMap.this.clear();
813     }
814     }
815    
816     /**
817 jsr166 1.14 * Returns a {@link Collection} view of the values contained in this map.
818     * The collection's iterator returns the values in ascending order
819     * of the corresponding keys.
820     * The collection is backed by the map, so changes to the map are
821     * reflected in the collection, and vice-versa. If the map is
822     * modified while an iteration over the collection is in progress
823     * (except through the iterator's own <tt>remove</tt> operation),
824     * the results of the iteration are undefined. The collection
825     * supports element removal, which removes the corresponding
826     * mapping from the map, via the <tt>Iterator.remove</tt>,
827     * <tt>Collection.remove</tt>, <tt>removeAll</tt>,
828     * <tt>retainAll</tt> and <tt>clear</tt> operations. It does not
829 jsr166 1.15 * support the <tt>add</tt> or <tt>addAll</tt> operations.
830 dl 1.1 */
831     public Collection<V> values() {
832     Collection<V> vs = values;
833     return (vs != null) ? vs : (values = new Values());
834     }
835    
836     class Values extends AbstractCollection<V> {
837     public Iterator<V> iterator() {
838     return new ValueIterator(getFirstEntry());
839     }
840 dl 1.8
841 dl 1.1 public int size() {
842     return TreeMap.this.size();
843     }
844 dl 1.8
845 dl 1.1 public boolean contains(Object o) {
846     for (Entry<K,V> e = getFirstEntry(); e != null; e = successor(e))
847     if (valEquals(e.getValue(), o))
848     return true;
849     return false;
850     }
851 dl 1.8
852 dl 1.1 public boolean remove(Object o) {
853     for (Entry<K,V> e = getFirstEntry(); e != null; e = successor(e)) {
854     if (valEquals(e.getValue(), o)) {
855     deleteEntry(e);
856     return true;
857     }
858     }
859     return false;
860     }
861 dl 1.8
862 dl 1.1 public void clear() {
863     TreeMap.this.clear();
864     }
865     }
866    
867     /**
868 jsr166 1.14 * Returns a {@link Set} view of the mappings contained in this map.
869     * The set's iterator returns the entries in ascending key order.
870     * The set is backed by the map, so changes to the map are
871     * reflected in the set, and vice-versa. If the map is modified
872     * while an iteration over the set is in progress (except through
873     * the iterator's own <tt>remove</tt> operation, or through the
874     * <tt>setValue</tt> operation on a map entry returned by the
875     * iterator) the results of the iteration are undefined. The set
876     * supports element removal, which removes the corresponding
877     * mapping from the map, via the <tt>Iterator.remove</tt>,
878 dl 1.1 * <tt>Set.remove</tt>, <tt>removeAll</tt>, <tt>retainAll</tt> and
879 jsr166 1.14 * <tt>clear</tt> operations. It does not support the
880     * <tt>add</tt> or <tt>addAll</tt> operations.
881 dl 1.1 */
882     public Set<Map.Entry<K,V>> entrySet() {
883     Set<Map.Entry<K,V>> es = entrySet;
884     return (es != null) ? es : (entrySet = new EntrySet());
885     }
886    
887     class EntrySet extends AbstractSet<Map.Entry<K,V>> {
888     public Iterator<Map.Entry<K,V>> iterator() {
889     return new EntryIterator(getFirstEntry());
890     }
891 dl 1.8
892 dl 1.1 public boolean contains(Object o) {
893     if (!(o instanceof Map.Entry))
894     return false;
895     Map.Entry<K,V> entry = (Map.Entry<K,V>) o;
896     V value = entry.getValue();
897     Entry<K,V> p = getEntry(entry.getKey());
898     return p != null && valEquals(p.getValue(), value);
899     }
900 dl 1.8
901 dl 1.1 public boolean remove(Object o) {
902     if (!(o instanceof Map.Entry))
903     return false;
904     Map.Entry<K,V> entry = (Map.Entry<K,V>) o;
905     V value = entry.getValue();
906     Entry<K,V> p = getEntry(entry.getKey());
907     if (p != null && valEquals(p.getValue(), value)) {
908     deleteEntry(p);
909     return true;
910     }
911     return false;
912     }
913 dl 1.8
914 dl 1.1 public int size() {
915     return TreeMap.this.size();
916     }
917 dl 1.8
918 dl 1.1 public void clear() {
919     TreeMap.this.clear();
920     }
921     }
922    
923     public Set<Map.Entry<K,V>> descendingEntrySet() {
924     Set<Map.Entry<K,V>> es = descendingEntrySet;
925     return (es != null) ? es : (descendingEntrySet = new DescendingEntrySet());
926     }
927    
928     class DescendingEntrySet extends EntrySet {
929     public Iterator<Map.Entry<K,V>> iterator() {
930     return new DescendingEntryIterator(getLastEntry());
931     }
932     }
933    
934     public Set<K> descendingKeySet() {
935     Set<K> ks = descendingKeySet;
936     return (ks != null) ? ks : (descendingKeySet = new DescendingKeySet());
937     }
938    
939     class DescendingKeySet extends KeySet {
940     public Iterator<K> iterator() {
941     return new DescendingKeyIterator(getLastEntry());
942     }
943     }
944    
945     /**
946 jsr166 1.14 * @throws ClassCastException {@inheritDoc}
947 dl 1.1 * @throws NullPointerException if <tt>fromKey</tt> or <tt>toKey</tt> is
948 jsr166 1.14 * null and this map uses natural ordering, or its comparator
949     * does not permit null keys
950     * @throws IllegalArgumentException {@inheritDoc}
951 dl 1.1 */
952 dl 1.4 public NavigableMap<K,V> navigableSubMap(K fromKey, K toKey) {
953 dl 1.1 return new SubMap(fromKey, toKey);
954     }
955    
956     /**
957 jsr166 1.14 * @throws ClassCastException {@inheritDoc}
958     * @throws NullPointerException if <tt>toKey</tt> is null
959     * and this map uses natural ordering, or its comparator
960     * does not permit null keys
961     * @throws IllegalArgumentException {@inheritDoc}
962 dl 1.1 */
963 dl 1.4 public NavigableMap<K,V> navigableHeadMap(K toKey) {
964 dl 1.1 return new SubMap(toKey, true);
965     }
966    
967     /**
968 jsr166 1.14 * @throws ClassCastException {@inheritDoc}
969     * @throws NullPointerException if <tt>fromKey</tt> is null
970     * and this map uses natural ordering, or its comparator
971     * does not permit null keys
972     * @throws IllegalArgumentException {@inheritDoc}
973 dl 1.1 */
974 dl 1.4 public NavigableMap<K,V> navigableTailMap(K fromKey) {
975     return new SubMap(fromKey, false);
976     }
977    
978     /**
979 jsr166 1.14 * Equivalent to {@link #navigableSubMap} but with a return type
980     * conforming to the <tt>SortedMap</tt> interface.
981     *
982     * <p>{@inheritDoc}
983     *
984     * @throws ClassCastException {@inheritDoc}
985 dl 1.4 * @throws NullPointerException if <tt>fromKey</tt> or <tt>toKey</tt> is
986 jsr166 1.14 * null and this map uses natural ordering, or its comparator
987     * does not permit null keys
988     * @throws IllegalArgumentException {@inheritDoc}
989 dl 1.4 */
990     public SortedMap<K,V> subMap(K fromKey, K toKey) {
991     return new SubMap(fromKey, toKey);
992     }
993    
994     /**
995 jsr166 1.14 * Equivalent to {@link #navigableHeadMap} but with a return type
996     * conforming to the <tt>SortedMap</tt> interface.
997     *
998     * <p>{@inheritDoc}
999 dl 1.4 *
1000 jsr166 1.14 * @throws ClassCastException {@inheritDoc}
1001     * @throws NullPointerException if <tt>toKey</tt> is null
1002     * and this map uses natural ordering, or its comparator
1003     * does not permit null keys
1004     * @throws IllegalArgumentException {@inheritDoc}
1005 dl 1.4 */
1006     public SortedMap<K,V> headMap(K toKey) {
1007     return new SubMap(toKey, true);
1008     }
1009    
1010     /**
1011 jsr166 1.14 * Equivalent to {@link #navigableTailMap} but with a return type
1012     * conforming to the <tt>SortedMap</tt> interface.
1013     *
1014     * <p>{@inheritDoc}
1015 dl 1.4 *
1016 jsr166 1.14 * @throws ClassCastException {@inheritDoc}
1017     * @throws NullPointerException if <tt>fromKey</tt> is null
1018     * and this map uses natural ordering, or its comparator
1019     * does not permit null keys
1020     * @throws IllegalArgumentException {@inheritDoc}
1021 dl 1.4 */
1022     public SortedMap<K,V> tailMap(K fromKey) {
1023 dl 1.1 return new SubMap(fromKey, false);
1024     }
1025    
1026     private class SubMap
1027     extends AbstractMap<K,V>
1028     implements NavigableMap<K,V>, java.io.Serializable {
1029     private static final long serialVersionUID = -6520786458950516097L;
1030    
1031     /**
1032     * fromKey is significant only if fromStart is false. Similarly,
1033     * toKey is significant only if toStart is false.
1034     */
1035     private boolean fromStart = false, toEnd = false;
1036     private K fromKey, toKey;
1037    
1038     SubMap(K fromKey, K toKey) {
1039     if (compare(fromKey, toKey) > 0)
1040     throw new IllegalArgumentException("fromKey > toKey");
1041     this.fromKey = fromKey;
1042     this.toKey = toKey;
1043     }
1044    
1045     SubMap(K key, boolean headMap) {
1046     compare(key, key); // Type-check key
1047    
1048     if (headMap) {
1049     fromStart = true;
1050     toKey = key;
1051     } else {
1052     toEnd = true;
1053     fromKey = key;
1054     }
1055     }
1056    
1057     SubMap(boolean fromStart, K fromKey, boolean toEnd, K toKey) {
1058     this.fromStart = fromStart;
1059     this.fromKey= fromKey;
1060     this.toEnd = toEnd;
1061     this.toKey = toKey;
1062     }
1063    
1064     public boolean isEmpty() {
1065 dl 1.7 return entrySet().isEmpty();
1066 dl 1.1 }
1067    
1068     public boolean containsKey(Object key) {
1069 dl 1.17 return inRange(key) && TreeMap.this.containsKey(key);
1070 dl 1.1 }
1071    
1072     public V get(Object key) {
1073 dl 1.17 if (!inRange(key))
1074 dl 1.1 return null;
1075     return TreeMap.this.get(key);
1076     }
1077    
1078     public V put(K key, V value) {
1079     if (!inRange(key))
1080     throw new IllegalArgumentException("key out of range");
1081     return TreeMap.this.put(key, value);
1082     }
1083    
1084     public V remove(Object key) {
1085 dl 1.17 if (!inRange(key))
1086 dl 1.1 return null;
1087     return TreeMap.this.remove(key);
1088     }
1089    
1090     public Comparator<? super K> comparator() {
1091     return comparator;
1092     }
1093    
1094     public K firstKey() {
1095     TreeMap.Entry<K,V> e = fromStart ? getFirstEntry() : getCeilingEntry(fromKey);
1096     K first = key(e);
1097     if (!toEnd && compare(first, toKey) >= 0)
1098 jsr166 1.11 throw new NoSuchElementException();
1099 dl 1.1 return first;
1100     }
1101    
1102     public K lastKey() {
1103     TreeMap.Entry<K,V> e = toEnd ? getLastEntry() : getLowerEntry(toKey);
1104     K last = key(e);
1105     if (!fromStart && compare(last, fromKey) < 0)
1106 jsr166 1.11 throw new NoSuchElementException();
1107 dl 1.1 return last;
1108     }
1109    
1110     public Map.Entry<K,V> firstEntry() {
1111 dl 1.8 TreeMap.Entry<K,V> e = fromStart ?
1112 dl 1.1 getFirstEntry() : getCeilingEntry(fromKey);
1113     if (e == null || (!toEnd && compare(e.key, toKey) >= 0))
1114     return null;
1115     return e;
1116     }
1117    
1118     public Map.Entry<K,V> lastEntry() {
1119 dl 1.8 TreeMap.Entry<K,V> e = toEnd ?
1120 dl 1.1 getLastEntry() : getLowerEntry(toKey);
1121     if (e == null || (!fromStart && compare(e.key, fromKey) < 0))
1122     return null;
1123     return e;
1124     }
1125    
1126     public Map.Entry<K,V> pollFirstEntry() {
1127 dl 1.8 TreeMap.Entry<K,V> e = fromStart ?
1128 dl 1.1 getFirstEntry() : getCeilingEntry(fromKey);
1129 dl 1.7 if (e == null || (!toEnd && compare(e.key, toKey) >= 0))
1130 dl 1.1 return null;
1131 dl 1.16 Map.Entry<K,V> result = new AbstractMap.SimpleImmutableEntry<K,V>(e);
1132 dl 1.1 deleteEntry(e);
1133     return result;
1134     }
1135    
1136     public Map.Entry<K,V> pollLastEntry() {
1137 dl 1.8 TreeMap.Entry<K,V> e = toEnd ?
1138 dl 1.1 getLastEntry() : getLowerEntry(toKey);
1139 dl 1.7 if (e == null || (!fromStart && compare(e.key, fromKey) < 0))
1140 dl 1.1 return null;
1141 dl 1.16 Map.Entry<K,V> result = new AbstractMap.SimpleImmutableEntry<K,V>(e);
1142 dl 1.1 deleteEntry(e);
1143     return result;
1144     }
1145    
1146     private TreeMap.Entry<K,V> subceiling(K key) {
1147     TreeMap.Entry<K,V> e = (!fromStart && compare(key, fromKey) < 0)?
1148     getCeilingEntry(fromKey) : getCeilingEntry(key);
1149     if (e == null || (!toEnd && compare(e.key, toKey) >= 0))
1150     return null;
1151     return e;
1152     }
1153    
1154     public Map.Entry<K,V> ceilingEntry(K key) {
1155     TreeMap.Entry<K,V> e = subceiling(key);
1156 dl 1.16 return e == null? null : new AbstractMap.SimpleImmutableEntry<K,V>(e);
1157 dl 1.1 }
1158    
1159     public K ceilingKey(K key) {
1160     TreeMap.Entry<K,V> e = subceiling(key);
1161     return e == null? null : e.key;
1162     }
1163    
1164    
1165     private TreeMap.Entry<K,V> subhigher(K key) {
1166     TreeMap.Entry<K,V> e = (!fromStart && compare(key, fromKey) < 0)?
1167     getCeilingEntry(fromKey) : getHigherEntry(key);
1168     if (e == null || (!toEnd && compare(e.key, toKey) >= 0))
1169     return null;
1170     return e;
1171     }
1172    
1173     public Map.Entry<K,V> higherEntry(K key) {
1174     TreeMap.Entry<K,V> e = subhigher(key);
1175 dl 1.16 return e == null? null : new AbstractMap.SimpleImmutableEntry<K,V>(e);
1176 dl 1.1 }
1177    
1178     public K higherKey(K key) {
1179     TreeMap.Entry<K,V> e = subhigher(key);
1180     return e == null? null : e.key;
1181     }
1182    
1183     private TreeMap.Entry<K,V> subfloor(K key) {
1184     TreeMap.Entry<K,V> e = (!toEnd && compare(key, toKey) >= 0)?
1185     getLowerEntry(toKey) : getFloorEntry(key);
1186     if (e == null || (!fromStart && compare(e.key, fromKey) < 0))
1187     return null;
1188     return e;
1189     }
1190    
1191     public Map.Entry<K,V> floorEntry(K key) {
1192     TreeMap.Entry<K,V> e = subfloor(key);
1193 dl 1.16 return e == null? null : new AbstractMap.SimpleImmutableEntry<K,V>(e);
1194 dl 1.1 }
1195    
1196     public K floorKey(K key) {
1197     TreeMap.Entry<K,V> e = subfloor(key);
1198     return e == null? null : e.key;
1199     }
1200    
1201     private TreeMap.Entry<K,V> sublower(K key) {
1202     TreeMap.Entry<K,V> e = (!toEnd && compare(key, toKey) >= 0)?
1203     getLowerEntry(toKey) : getLowerEntry(key);
1204     if (e == null || (!fromStart && compare(e.key, fromKey) < 0))
1205     return null;
1206     return e;
1207     }
1208    
1209     public Map.Entry<K,V> lowerEntry(K key) {
1210     TreeMap.Entry<K,V> e = sublower(key);
1211 dl 1.16 return e == null? null : new AbstractMap.SimpleImmutableEntry<K,V>(e);
1212 dl 1.1 }
1213    
1214     public K lowerKey(K key) {
1215     TreeMap.Entry<K,V> e = sublower(key);
1216     return e == null? null : e.key;
1217     }
1218    
1219 dl 1.7 private transient Set<Map.Entry<K,V>> entrySet = null;
1220 dl 1.1
1221     public Set<Map.Entry<K,V>> entrySet() {
1222 dl 1.7 Set<Map.Entry<K,V>> es = entrySet;
1223     return (es != null)? es : (entrySet = new EntrySetView());
1224 dl 1.1 }
1225    
1226     private class EntrySetView extends AbstractSet<Map.Entry<K,V>> {
1227     private transient int size = -1, sizeModCount;
1228    
1229     public int size() {
1230     if (size == -1 || sizeModCount != TreeMap.this.modCount) {
1231     size = 0; sizeModCount = TreeMap.this.modCount;
1232     Iterator i = iterator();
1233     while (i.hasNext()) {
1234     size++;
1235     i.next();
1236     }
1237     }
1238     return size;
1239     }
1240    
1241     public boolean isEmpty() {
1242     return !iterator().hasNext();
1243     }
1244    
1245     public boolean contains(Object o) {
1246     if (!(o instanceof Map.Entry))
1247     return false;
1248     Map.Entry<K,V> entry = (Map.Entry<K,V>) o;
1249     K key = entry.getKey();
1250     if (!inRange(key))
1251     return false;
1252     TreeMap.Entry node = getEntry(key);
1253     return node != null &&
1254     valEquals(node.getValue(), entry.getValue());
1255     }
1256    
1257     public boolean remove(Object o) {
1258     if (!(o instanceof Map.Entry))
1259     return false;
1260     Map.Entry<K,V> entry = (Map.Entry<K,V>) o;
1261     K key = entry.getKey();
1262     if (!inRange(key))
1263     return false;
1264     TreeMap.Entry<K,V> node = getEntry(key);
1265     if (node!=null && valEquals(node.getValue(),entry.getValue())){
1266     deleteEntry(node);
1267     return true;
1268     }
1269     return false;
1270     }
1271    
1272     public Iterator<Map.Entry<K,V>> iterator() {
1273     return new SubMapEntryIterator(
1274     (fromStart ? getFirstEntry() : getCeilingEntry(fromKey)),
1275     (toEnd ? null : getCeilingEntry(toKey)));
1276     }
1277     }
1278    
1279     private transient Set<Map.Entry<K,V>> descendingEntrySetView = null;
1280 dl 1.8 private transient Set<K> descendingKeySetView = null;
1281 dl 1.1
1282     public Set<Map.Entry<K,V>> descendingEntrySet() {
1283     Set<Map.Entry<K,V>> es = descendingEntrySetView;
1284 jsr166 1.14 return (es != null) ? es :
1285     (descendingEntrySetView = new DescendingEntrySetView());
1286 dl 1.1 }
1287    
1288     public Set<K> descendingKeySet() {
1289     Set<K> ks = descendingKeySetView;
1290 jsr166 1.14 return (ks != null) ? ks :
1291     (descendingKeySetView = new DescendingKeySetView());
1292 dl 1.1 }
1293    
1294     private class DescendingEntrySetView extends EntrySetView {
1295     public Iterator<Map.Entry<K,V>> iterator() {
1296     return new DescendingSubMapEntryIterator
1297     ((toEnd ? getLastEntry() : getLowerEntry(toKey)),
1298     (fromStart ? null : getLowerEntry(fromKey)));
1299     }
1300     }
1301    
1302     private class DescendingKeySetView extends AbstractSet<K> {
1303     public Iterator<K> iterator() {
1304     return new Iterator<K>() {
1305     private Iterator<Entry<K,V>> i = descendingEntrySet().iterator();
1306 dl 1.8
1307 dl 1.1 public boolean hasNext() { return i.hasNext(); }
1308     public K next() { return i.next().getKey(); }
1309     public void remove() { i.remove(); }
1310     };
1311     }
1312 dl 1.8
1313 dl 1.1 public int size() {
1314     return SubMap.this.size();
1315     }
1316 dl 1.8
1317 dl 1.1 public boolean contains(Object k) {
1318     return SubMap.this.containsKey(k);
1319     }
1320     }
1321    
1322 dl 1.4 public NavigableMap<K,V> navigableSubMap(K fromKey, K toKey) {
1323 dl 1.1 if (!inRange2(fromKey))
1324     throw new IllegalArgumentException("fromKey out of range");
1325     if (!inRange2(toKey))
1326     throw new IllegalArgumentException("toKey out of range");
1327     return new SubMap(fromKey, toKey);
1328     }
1329    
1330 dl 1.4 public NavigableMap<K,V> navigableHeadMap(K toKey) {
1331 dl 1.1 if (!inRange2(toKey))
1332     throw new IllegalArgumentException("toKey out of range");
1333     return new SubMap(fromStart, fromKey, false, toKey);
1334     }
1335    
1336 dl 1.4 public NavigableMap<K,V> navigableTailMap(K fromKey) {
1337 dl 1.1 if (!inRange2(fromKey))
1338     throw new IllegalArgumentException("fromKey out of range");
1339     return new SubMap(false, fromKey, toEnd, toKey);
1340     }
1341    
1342 dl 1.4 public SortedMap<K,V> subMap(K fromKey, K toKey) {
1343     return navigableSubMap(fromKey, toKey);
1344     }
1345    
1346     public SortedMap<K,V> headMap(K toKey) {
1347     return navigableHeadMap(toKey);
1348     }
1349    
1350     public SortedMap<K,V> tailMap(K fromKey) {
1351     return navigableTailMap(fromKey);
1352     }
1353    
1354 dl 1.17 private boolean inRange(Object key) {
1355 dl 1.1 return (fromStart || compare(key, fromKey) >= 0) &&
1356     (toEnd || compare(key, toKey) < 0);
1357     }
1358    
1359     // This form allows the high endpoint (as well as all legit keys)
1360 dl 1.17 private boolean inRange2(Object key) {
1361 dl 1.1 return (fromStart || compare(key, fromKey) >= 0) &&
1362     (toEnd || compare(key, toKey) <= 0);
1363     }
1364     }
1365    
1366     /**
1367     * TreeMap Iterator.
1368     */
1369     abstract class PrivateEntryIterator<T> implements Iterator<T> {
1370     int expectedModCount = TreeMap.this.modCount;
1371     Entry<K,V> lastReturned = null;
1372     Entry<K,V> next;
1373    
1374     PrivateEntryIterator(Entry<K,V> first) {
1375     next = first;
1376     }
1377    
1378     public boolean hasNext() {
1379     return next != null;
1380     }
1381    
1382 jsr166 1.14 Entry<K,V> nextEntry() {
1383 dl 1.1 if (next == null)
1384     throw new NoSuchElementException();
1385     if (modCount != expectedModCount)
1386     throw new ConcurrentModificationException();
1387     lastReturned = next;
1388     next = successor(next);
1389     return lastReturned;
1390     }
1391    
1392     public void remove() {
1393     if (lastReturned == null)
1394     throw new IllegalStateException();
1395     if (modCount != expectedModCount)
1396     throw new ConcurrentModificationException();
1397     if (lastReturned.left != null && lastReturned.right != null)
1398     next = lastReturned;
1399     deleteEntry(lastReturned);
1400     expectedModCount++;
1401     lastReturned = null;
1402     }
1403     }
1404    
1405     class EntryIterator extends PrivateEntryIterator<Map.Entry<K,V>> {
1406     EntryIterator(Entry<K,V> first) {
1407     super(first);
1408     }
1409     public Map.Entry<K,V> next() {
1410     return nextEntry();
1411     }
1412     }
1413    
1414     class KeyIterator extends PrivateEntryIterator<K> {
1415     KeyIterator(Entry<K,V> first) {
1416     super(first);
1417     }
1418     public K next() {
1419     return nextEntry().key;
1420     }
1421     }
1422    
1423     class ValueIterator extends PrivateEntryIterator<V> {
1424     ValueIterator(Entry<K,V> first) {
1425     super(first);
1426     }
1427     public V next() {
1428     return nextEntry().value;
1429     }
1430     }
1431    
1432     class SubMapEntryIterator extends PrivateEntryIterator<Map.Entry<K,V>> {
1433     private final K firstExcludedKey;
1434    
1435     SubMapEntryIterator(Entry<K,V> first, Entry<K,V> firstExcluded) {
1436     super(first);
1437     firstExcludedKey = (firstExcluded == null
1438     ? null
1439     : firstExcluded.key);
1440     }
1441    
1442     public boolean hasNext() {
1443     return next != null && next.key != firstExcludedKey;
1444     }
1445    
1446     public Map.Entry<K,V> next() {
1447     if (next == null || next.key == firstExcludedKey)
1448     throw new NoSuchElementException();
1449     return nextEntry();
1450     }
1451     }
1452    
1453     /**
1454     * Base for Descending Iterators.
1455     */
1456     abstract class DescendingPrivateEntryIterator<T> extends PrivateEntryIterator<T> {
1457     DescendingPrivateEntryIterator(Entry<K,V> first) {
1458     super(first);
1459     }
1460    
1461     Entry<K,V> nextEntry() {
1462     if (next == null)
1463     throw new NoSuchElementException();
1464     if (modCount != expectedModCount)
1465     throw new ConcurrentModificationException();
1466     lastReturned = next;
1467     next = predecessor(next);
1468     return lastReturned;
1469     }
1470     }
1471    
1472     class DescendingEntryIterator extends DescendingPrivateEntryIterator<Map.Entry<K,V>> {
1473     DescendingEntryIterator(Entry<K,V> first) {
1474     super(first);
1475     }
1476     public Map.Entry<K,V> next() {
1477     return nextEntry();
1478     }
1479     }
1480    
1481     class DescendingKeyIterator extends DescendingPrivateEntryIterator<K> {
1482     DescendingKeyIterator(Entry<K,V> first) {
1483     super(first);
1484     }
1485     public K next() {
1486     return nextEntry().key;
1487     }
1488     }
1489    
1490    
1491     class DescendingSubMapEntryIterator extends DescendingPrivateEntryIterator<Map.Entry<K,V>> {
1492     private final K lastExcludedKey;
1493    
1494     DescendingSubMapEntryIterator(Entry<K,V> last, Entry<K,V> lastExcluded) {
1495     super(last);
1496     lastExcludedKey = (lastExcluded == null
1497     ? null
1498     : lastExcluded.key);
1499     }
1500    
1501     public boolean hasNext() {
1502     return next != null && next.key != lastExcludedKey;
1503     }
1504    
1505     public Map.Entry<K,V> next() {
1506     if (next == null || next.key == lastExcludedKey)
1507     throw new NoSuchElementException();
1508     return nextEntry();
1509     }
1510    
1511     }
1512    
1513     /**
1514     * Compares two keys using the correct comparison method for this TreeMap.
1515     */
1516 dl 1.16 private int compare(Object k1, Object k2) {
1517     return comparator==null ? ((Comparable<? super K>)k1).compareTo((K)k2)
1518     : comparator.compare((K)k1, (K)k2);
1519 dl 1.1 }
1520    
1521     /**
1522     * Test two values for equality. Differs from o1.equals(o2) only in
1523     * that it copes with <tt>null</tt> o1 properly.
1524     */
1525     private static boolean valEquals(Object o1, Object o2) {
1526     return (o1==null ? o2==null : o1.equals(o2));
1527     }
1528    
1529     private static final boolean RED = false;
1530     private static final boolean BLACK = true;
1531    
1532     /**
1533     * Node in the Tree. Doubles as a means to pass key-value pairs back to
1534     * user (see Map.Entry).
1535     */
1536    
1537     static class Entry<K,V> implements Map.Entry<K,V> {
1538     K key;
1539     V value;
1540     Entry<K,V> left = null;
1541     Entry<K,V> right = null;
1542     Entry<K,V> parent;
1543     boolean color = BLACK;
1544    
1545     /**
1546     * Make a new cell with given key, value, and parent, and with
1547     * <tt>null</tt> child links, and BLACK color.
1548     */
1549     Entry(K key, V value, Entry<K,V> parent) {
1550     this.key = key;
1551     this.value = value;
1552     this.parent = parent;
1553     }
1554    
1555     /**
1556     * Returns the key.
1557     *
1558 jsr166 1.14 * @return the key
1559 dl 1.1 */
1560     public K getKey() {
1561     return key;
1562     }
1563    
1564     /**
1565     * Returns the value associated with the key.
1566     *
1567 jsr166 1.14 * @return the value associated with the key
1568 dl 1.1 */
1569     public V getValue() {
1570     return value;
1571     }
1572    
1573     /**
1574     * Replaces the value currently associated with the key with the given
1575     * value.
1576     *
1577     * @return the value associated with the key before this method was
1578 jsr166 1.14 * called
1579 dl 1.1 */
1580     public V setValue(V value) {
1581     V oldValue = this.value;
1582     this.value = value;
1583     return oldValue;
1584     }
1585    
1586     public boolean equals(Object o) {
1587     if (!(o instanceof Map.Entry))
1588     return false;
1589     Map.Entry e = (Map.Entry)o;
1590    
1591     return valEquals(key,e.getKey()) && valEquals(value,e.getValue());
1592     }
1593    
1594     public int hashCode() {
1595     int keyHash = (key==null ? 0 : key.hashCode());
1596     int valueHash = (value==null ? 0 : value.hashCode());
1597     return keyHash ^ valueHash;
1598     }
1599    
1600     public String toString() {
1601     return key + "=" + value;
1602     }
1603     }
1604    
1605     /**
1606     * Returns the first Entry in the TreeMap (according to the TreeMap's
1607     * key-sort function). Returns null if the TreeMap is empty.
1608     */
1609     private Entry<K,V> getFirstEntry() {
1610     Entry<K,V> p = root;
1611     if (p != null)
1612     while (p.left != null)
1613     p = p.left;
1614     return p;
1615     }
1616    
1617     /**
1618     * Returns the last Entry in the TreeMap (according to the TreeMap's
1619     * key-sort function). Returns null if the TreeMap is empty.
1620     */
1621     private Entry<K,V> getLastEntry() {
1622     Entry<K,V> p = root;
1623     if (p != null)
1624     while (p.right != null)
1625     p = p.right;
1626     return p;
1627     }
1628    
1629     /**
1630     * Returns the successor of the specified Entry, or null if no such.
1631     */
1632     private Entry<K,V> successor(Entry<K,V> t) {
1633     if (t == null)
1634     return null;
1635     else if (t.right != null) {
1636     Entry<K,V> p = t.right;
1637     while (p.left != null)
1638     p = p.left;
1639     return p;
1640     } else {
1641     Entry<K,V> p = t.parent;
1642     Entry<K,V> ch = t;
1643     while (p != null && ch == p.right) {
1644     ch = p;
1645     p = p.parent;
1646     }
1647     return p;
1648     }
1649     }
1650    
1651     /**
1652     * Returns the predecessor of the specified Entry, or null if no such.
1653     */
1654     private Entry<K,V> predecessor(Entry<K,V> t) {
1655     if (t == null)
1656     return null;
1657     else if (t.left != null) {
1658     Entry<K,V> p = t.left;
1659     while (p.right != null)
1660     p = p.right;
1661     return p;
1662     } else {
1663     Entry<K,V> p = t.parent;
1664     Entry<K,V> ch = t;
1665     while (p != null && ch == p.left) {
1666     ch = p;
1667     p = p.parent;
1668     }
1669     return p;
1670     }
1671     }
1672    
1673     /**
1674     * Balancing operations.
1675     *
1676     * Implementations of rebalancings during insertion and deletion are
1677     * slightly different than the CLR version. Rather than using dummy
1678     * nilnodes, we use a set of accessors that deal properly with null. They
1679     * are used to avoid messiness surrounding nullness checks in the main
1680     * algorithms.
1681     */
1682    
1683     private static <K,V> boolean colorOf(Entry<K,V> p) {
1684     return (p == null ? BLACK : p.color);
1685     }
1686    
1687     private static <K,V> Entry<K,V> parentOf(Entry<K,V> p) {
1688     return (p == null ? null: p.parent);
1689     }
1690    
1691     private static <K,V> void setColor(Entry<K,V> p, boolean c) {
1692     if (p != null)
1693     p.color = c;
1694     }
1695    
1696     private static <K,V> Entry<K,V> leftOf(Entry<K,V> p) {
1697     return (p == null) ? null: p.left;
1698     }
1699    
1700     private static <K,V> Entry<K,V> rightOf(Entry<K,V> p) {
1701     return (p == null) ? null: p.right;
1702     }
1703    
1704     /** From CLR **/
1705     private void rotateLeft(Entry<K,V> p) {
1706     Entry<K,V> r = p.right;
1707     p.right = r.left;
1708     if (r.left != null)
1709     r.left.parent = p;
1710     r.parent = p.parent;
1711     if (p.parent == null)
1712     root = r;
1713     else if (p.parent.left == p)
1714     p.parent.left = r;
1715     else
1716     p.parent.right = r;
1717     r.left = p;
1718     p.parent = r;
1719     }
1720    
1721     /** From CLR **/
1722     private void rotateRight(Entry<K,V> p) {
1723     Entry<K,V> l = p.left;
1724     p.left = l.right;
1725     if (l.right != null) l.right.parent = p;
1726     l.parent = p.parent;
1727     if (p.parent == null)
1728     root = l;
1729     else if (p.parent.right == p)
1730     p.parent.right = l;
1731     else p.parent.left = l;
1732     l.right = p;
1733     p.parent = l;
1734     }
1735    
1736    
1737     /** From CLR **/
1738     private void fixAfterInsertion(Entry<K,V> x) {
1739     x.color = RED;
1740    
1741     while (x != null && x != root && x.parent.color == RED) {
1742     if (parentOf(x) == leftOf(parentOf(parentOf(x)))) {
1743     Entry<K,V> y = rightOf(parentOf(parentOf(x)));
1744     if (colorOf(y) == RED) {
1745     setColor(parentOf(x), BLACK);
1746     setColor(y, BLACK);
1747     setColor(parentOf(parentOf(x)), RED);
1748     x = parentOf(parentOf(x));
1749     } else {
1750     if (x == rightOf(parentOf(x))) {
1751     x = parentOf(x);
1752     rotateLeft(x);
1753     }
1754     setColor(parentOf(x), BLACK);
1755     setColor(parentOf(parentOf(x)), RED);
1756     if (parentOf(parentOf(x)) != null)
1757     rotateRight(parentOf(parentOf(x)));
1758     }
1759     } else {
1760     Entry<K,V> y = leftOf(parentOf(parentOf(x)));
1761     if (colorOf(y) == RED) {
1762     setColor(parentOf(x), BLACK);
1763     setColor(y, BLACK);
1764     setColor(parentOf(parentOf(x)), RED);
1765     x = parentOf(parentOf(x));
1766     } else {
1767     if (x == leftOf(parentOf(x))) {
1768     x = parentOf(x);
1769     rotateRight(x);
1770     }
1771     setColor(parentOf(x), BLACK);
1772     setColor(parentOf(parentOf(x)), RED);
1773     if (parentOf(parentOf(x)) != null)
1774     rotateLeft(parentOf(parentOf(x)));
1775     }
1776     }
1777     }
1778     root.color = BLACK;
1779     }
1780    
1781     /**
1782     * Delete node p, and then rebalance the tree.
1783     */
1784    
1785     private void deleteEntry(Entry<K,V> p) {
1786     decrementSize();
1787    
1788     // If strictly internal, copy successor's element to p and then make p
1789     // point to successor.
1790     if (p.left != null && p.right != null) {
1791     Entry<K,V> s = successor (p);
1792     p.key = s.key;
1793     p.value = s.value;
1794     p = s;
1795     } // p has 2 children
1796    
1797     // Start fixup at replacement node, if it exists.
1798     Entry<K,V> replacement = (p.left != null ? p.left : p.right);
1799    
1800     if (replacement != null) {
1801     // Link replacement to parent
1802     replacement.parent = p.parent;
1803     if (p.parent == null)
1804     root = replacement;
1805     else if (p == p.parent.left)
1806     p.parent.left = replacement;
1807     else
1808     p.parent.right = replacement;
1809    
1810     // Null out links so they are OK to use by fixAfterDeletion.
1811     p.left = p.right = p.parent = null;
1812    
1813     // Fix replacement
1814     if (p.color == BLACK)
1815     fixAfterDeletion(replacement);
1816     } else if (p.parent == null) { // return if we are the only node.
1817     root = null;
1818     } else { // No children. Use self as phantom replacement and unlink.
1819     if (p.color == BLACK)
1820     fixAfterDeletion(p);
1821    
1822     if (p.parent != null) {
1823     if (p == p.parent.left)
1824     p.parent.left = null;
1825     else if (p == p.parent.right)
1826     p.parent.right = null;
1827     p.parent = null;
1828     }
1829     }
1830     }
1831    
1832     /** From CLR **/
1833     private void fixAfterDeletion(Entry<K,V> x) {
1834     while (x != root && colorOf(x) == BLACK) {
1835     if (x == leftOf(parentOf(x))) {
1836     Entry<K,V> sib = rightOf(parentOf(x));
1837    
1838     if (colorOf(sib) == RED) {
1839     setColor(sib, BLACK);
1840     setColor(parentOf(x), RED);
1841     rotateLeft(parentOf(x));
1842     sib = rightOf(parentOf(x));
1843     }
1844    
1845     if (colorOf(leftOf(sib)) == BLACK &&
1846     colorOf(rightOf(sib)) == BLACK) {
1847     setColor(sib, RED);
1848     x = parentOf(x);
1849     } else {
1850     if (colorOf(rightOf(sib)) == BLACK) {
1851     setColor(leftOf(sib), BLACK);
1852     setColor(sib, RED);
1853     rotateRight(sib);
1854     sib = rightOf(parentOf(x));
1855     }
1856     setColor(sib, colorOf(parentOf(x)));
1857     setColor(parentOf(x), BLACK);
1858     setColor(rightOf(sib), BLACK);
1859     rotateLeft(parentOf(x));
1860     x = root;
1861     }
1862     } else { // symmetric
1863     Entry<K,V> sib = leftOf(parentOf(x));
1864    
1865     if (colorOf(sib) == RED) {
1866     setColor(sib, BLACK);
1867     setColor(parentOf(x), RED);
1868     rotateRight(parentOf(x));
1869     sib = leftOf(parentOf(x));
1870     }
1871    
1872     if (colorOf(rightOf(sib)) == BLACK &&
1873     colorOf(leftOf(sib)) == BLACK) {
1874     setColor(sib, RED);
1875     x = parentOf(x);
1876     } else {
1877     if (colorOf(leftOf(sib)) == BLACK) {
1878     setColor(rightOf(sib), BLACK);
1879     setColor(sib, RED);
1880     rotateLeft(sib);
1881     sib = leftOf(parentOf(x));
1882     }
1883     setColor(sib, colorOf(parentOf(x)));
1884     setColor(parentOf(x), BLACK);
1885     setColor(leftOf(sib), BLACK);
1886     rotateRight(parentOf(x));
1887     x = root;
1888     }
1889     }
1890     }
1891    
1892     setColor(x, BLACK);
1893     }
1894    
1895     private static final long serialVersionUID = 919286545866124006L;
1896    
1897     /**
1898     * Save the state of the <tt>TreeMap</tt> instance to a stream (i.e.,
1899     * serialize it).
1900     *
1901     * @serialData The <i>size</i> of the TreeMap (the number of key-value
1902     * mappings) is emitted (int), followed by the key (Object)
1903     * and value (Object) for each key-value mapping represented
1904     * by the TreeMap. The key-value mappings are emitted in
1905     * key-order (as determined by the TreeMap's Comparator,
1906     * or by the keys' natural ordering if the TreeMap has no
1907     * Comparator).
1908     */
1909     private void writeObject(java.io.ObjectOutputStream s)
1910     throws java.io.IOException {
1911     // Write out the Comparator and any hidden stuff
1912     s.defaultWriteObject();
1913    
1914     // Write out size (number of Mappings)
1915     s.writeInt(size);
1916    
1917     // Write out keys and values (alternating)
1918 jsr166 1.14 for (Iterator<Map.Entry<K,V>> i = entrySet().iterator(); i.hasNext(); ) {
1919 dl 1.1 Map.Entry<K,V> e = i.next();
1920     s.writeObject(e.getKey());
1921     s.writeObject(e.getValue());
1922     }
1923     }
1924    
1925    
1926    
1927     /**
1928     * Reconstitute the <tt>TreeMap</tt> instance from a stream (i.e.,
1929     * deserialize it).
1930     */
1931     private void readObject(final java.io.ObjectInputStream s)
1932     throws java.io.IOException, ClassNotFoundException {
1933     // Read in the Comparator and any hidden stuff
1934     s.defaultReadObject();
1935    
1936     // Read in size
1937     int size = s.readInt();
1938    
1939     buildFromSorted(size, null, s, null);
1940     }
1941    
1942     /** Intended to be called only from TreeSet.readObject **/
1943     void readTreeSet(int size, java.io.ObjectInputStream s, V defaultVal)
1944     throws java.io.IOException, ClassNotFoundException {
1945     buildFromSorted(size, null, s, defaultVal);
1946     }
1947    
1948     /** Intended to be called only from TreeSet.addAll **/
1949 jsr166 1.12 void addAllForTreeSet(SortedSet<? extends K> set, V defaultVal) {
1950 dl 1.1 try {
1951     buildFromSorted(set.size(), set.iterator(), null, defaultVal);
1952     } catch (java.io.IOException cannotHappen) {
1953     } catch (ClassNotFoundException cannotHappen) {
1954     }
1955     }
1956    
1957    
1958     /**
1959     * Linear time tree building algorithm from sorted data. Can accept keys
1960     * and/or values from iterator or stream. This leads to too many
1961     * parameters, but seems better than alternatives. The four formats
1962     * that this method accepts are:
1963     *
1964     * 1) An iterator of Map.Entries. (it != null, defaultVal == null).
1965     * 2) An iterator of keys. (it != null, defaultVal != null).
1966     * 3) A stream of alternating serialized keys and values.
1967     * (it == null, defaultVal == null).
1968     * 4) A stream of serialized keys. (it == null, defaultVal != null).
1969     *
1970     * It is assumed that the comparator of the TreeMap is already set prior
1971     * to calling this method.
1972     *
1973     * @param size the number of keys (or key-value pairs) to be read from
1974 jsr166 1.14 * the iterator or stream
1975 dl 1.1 * @param it If non-null, new entries are created from entries
1976     * or keys read from this iterator.
1977     * @param str If non-null, new entries are created from keys and
1978     * possibly values read from this stream in serialized form.
1979     * Exactly one of it and str should be non-null.
1980     * @param defaultVal if non-null, this default value is used for
1981     * each value in the map. If null, each value is read from
1982     * iterator or stream, as described above.
1983     * @throws IOException propagated from stream reads. This cannot
1984     * occur if str is null.
1985     * @throws ClassNotFoundException propagated from readObject.
1986     * This cannot occur if str is null.
1987     */
1988     private
1989     void buildFromSorted(int size, Iterator it,
1990     java.io.ObjectInputStream str,
1991     V defaultVal)
1992     throws java.io.IOException, ClassNotFoundException {
1993     this.size = size;
1994     root =
1995     buildFromSorted(0, 0, size-1, computeRedLevel(size),
1996     it, str, defaultVal);
1997     }
1998    
1999     /**
2000     * Recursive "helper method" that does the real work of the
2001     * of the previous method. Identically named parameters have
2002     * identical definitions. Additional parameters are documented below.
2003     * It is assumed that the comparator and size fields of the TreeMap are
2004     * already set prior to calling this method. (It ignores both fields.)
2005     *
2006     * @param level the current level of tree. Initial call should be 0.
2007     * @param lo the first element index of this subtree. Initial should be 0.
2008     * @param hi the last element index of this subtree. Initial should be
2009 jsr166 1.14 * size-1.
2010 dl 1.1 * @param redLevel the level at which nodes should be red.
2011     * Must be equal to computeRedLevel for tree of this size.
2012     */
2013     private final Entry<K,V> buildFromSorted(int level, int lo, int hi,
2014     int redLevel,
2015     Iterator it,
2016     java.io.ObjectInputStream str,
2017     V defaultVal)
2018     throws java.io.IOException, ClassNotFoundException {
2019     /*
2020     * Strategy: The root is the middlemost element. To get to it, we
2021     * have to first recursively construct the entire left subtree,
2022     * so as to grab all of its elements. We can then proceed with right
2023     * subtree.
2024     *
2025     * The lo and hi arguments are the minimum and maximum
2026     * indices to pull out of the iterator or stream for current subtree.
2027     * They are not actually indexed, we just proceed sequentially,
2028     * ensuring that items are extracted in corresponding order.
2029     */
2030    
2031     if (hi < lo) return null;
2032    
2033     int mid = (lo + hi) / 2;
2034    
2035     Entry<K,V> left = null;
2036     if (lo < mid)
2037     left = buildFromSorted(level+1, lo, mid - 1, redLevel,
2038     it, str, defaultVal);
2039    
2040     // extract key and/or value from iterator or stream
2041     K key;
2042     V value;
2043     if (it != null) {
2044     if (defaultVal==null) {
2045     Map.Entry<K,V> entry = (Map.Entry<K,V>)it.next();
2046     key = entry.getKey();
2047     value = entry.getValue();
2048     } else {
2049     key = (K)it.next();
2050     value = defaultVal;
2051     }
2052     } else { // use stream
2053     key = (K) str.readObject();
2054     value = (defaultVal != null ? defaultVal : (V) str.readObject());
2055     }
2056    
2057     Entry<K,V> middle = new Entry<K,V>(key, value, null);
2058    
2059     // color nodes in non-full bottommost level red
2060     if (level == redLevel)
2061     middle.color = RED;
2062    
2063     if (left != null) {
2064     middle.left = left;
2065     left.parent = middle;
2066     }
2067    
2068     if (mid < hi) {
2069     Entry<K,V> right = buildFromSorted(level+1, mid+1, hi, redLevel,
2070     it, str, defaultVal);
2071     middle.right = right;
2072     right.parent = middle;
2073     }
2074    
2075     return middle;
2076     }
2077    
2078     /**
2079     * Find the level down to which to assign all nodes BLACK. This is the
2080     * last `full' level of the complete binary tree produced by
2081     * buildTree. The remaining nodes are colored RED. (This makes a `nice'
2082     * set of color assignments wrt future insertions.) This level number is
2083     * computed by finding the number of splits needed to reach the zeroeth
2084     * node. (The answer is ~lg(N), but in any case must be computed by same
2085     * quick O(lg(N)) loop.)
2086     */
2087     private static int computeRedLevel(int sz) {
2088     int level = 0;
2089     for (int m = sz - 1; m >= 0; m = m / 2 - 1)
2090     level++;
2091     return level;
2092     }
2093     }