1 |
|
/* |
2 |
|
* %W% %E% |
3 |
|
* |
4 |
< |
* Copyright 2004 Sun Microsystems, Inc. All rights reserved. |
4 |
> |
* Copyright 2006 Sun Microsystems, Inc. All rights reserved. |
5 |
|
* SUN PROPRIETARY/CONFIDENTIAL. Use is subject to license terms. |
6 |
|
*/ |
7 |
|
|
37 |
|
* example, invoking the <tt>sort</tt> method on an unmodifiable list that is |
38 |
|
* already sorted may or may not throw <tt>UnsupportedOperationException</tt>. |
39 |
|
* |
40 |
< |
* <p>This class is a member of the |
40 |
> |
* <p>This class is a member of the |
41 |
|
* <a href="{@docRoot}/../guide/collections/index.html"> |
42 |
|
* Java Collections Framework</a>. |
43 |
|
* |
63 |
|
* two implementations, one of which is appropriate for RandomAccess |
64 |
|
* lists, the other for "sequential." Often, the random access variant |
65 |
|
* yields better performance on small sequential access lists. The |
66 |
< |
* tuning parameters below determine the cutoff point for what constitutes |
66 |
> |
* tuning parameters below determine the cutoff point for what constitutes |
67 |
|
* a "small" sequential access list for each algorithm. The values below |
68 |
|
* were empirically determined to work well for LinkedList. Hopefully |
69 |
|
* they should be reasonable for other sequential access List |
97 |
|
* The sorting algorithm is a modified mergesort (in which the merge is |
98 |
|
* omitted if the highest element in the low sublist is less than the |
99 |
|
* lowest element in the high sublist). This algorithm offers guaranteed |
100 |
< |
* n log(n) performance. |
100 |
> |
* n log(n) performance. |
101 |
|
* |
102 |
|
* This implementation dumps the specified list into an array, sorts |
103 |
|
* the array, and iterates over the list resetting each element |
135 |
|
* The sorting algorithm is a modified mergesort (in which the merge is |
136 |
|
* omitted if the highest element in the low sublist is less than the |
137 |
|
* lowest element in the high sublist). This algorithm offers guaranteed |
138 |
< |
* n log(n) performance. |
138 |
> |
* n log(n) performance. |
139 |
|
* |
140 |
|
* The specified list must be modifiable, but need not be resizable. |
141 |
|
* This implementation dumps the specified list into an array, sorts |
182 |
|
* |
183 |
|
* @param list the list to be searched. |
184 |
|
* @param key the key to be searched for. |
185 |
< |
* @return index of the search key, if it is contained in the list; |
185 |
> |
* @return the index of the search key, if it is contained in the list; |
186 |
|
* otherwise, <tt>(-(<i>insertion point</i>) - 1)</tt>. The |
187 |
|
* <i>insertion point</i> is defined as the point at which the |
188 |
|
* key would be inserted into the list: the index of the first |
287 |
|
* @param c the comparator by which the list is ordered. A |
288 |
|
* <tt>null</tt> value indicates that the elements' <i>natural |
289 |
|
* ordering</i> should be used. |
290 |
< |
* @return index of the search key, if it is contained in the list; |
290 |
> |
* @return the index of the search key, if it is contained in the list; |
291 |
|
* otherwise, <tt>(-(<i>insertion point</i>) - 1)</tt>. The |
292 |
|
* <i>insertion point</i> is defined as the point at which the |
293 |
|
* key would be inserted into the list: the index of the first |
361 |
|
* |
362 |
|
* @param list the list whose elements are to be reversed. |
363 |
|
* @throws UnsupportedOperationException if the specified list or |
364 |
< |
* its list-iterator does not support the <tt>set</tt> method. |
364 |
> |
* its list-iterator does not support the <tt>set</tt> operation. |
365 |
|
*/ |
366 |
|
public static void reverse(List<?> list) { |
367 |
|
int size = list.size(); |
405 |
|
* |
406 |
|
* @param list the list to be shuffled. |
407 |
|
* @throws UnsupportedOperationException if the specified list or |
408 |
< |
* its list-iterator does not support the <tt>set</tt> method. |
408 |
> |
* its list-iterator does not support the <tt>set</tt> operation. |
409 |
|
*/ |
410 |
|
public static void shuffle(List<?> list) { |
411 |
+ |
if (r == null) { |
412 |
+ |
r = new Random(); |
413 |
+ |
} |
414 |
|
shuffle(list, r); |
415 |
|
} |
416 |
< |
private static Random r = new Random(); |
416 |
> |
private static Random r; |
417 |
|
|
418 |
|
/** |
419 |
|
* Randomly permute the specified list using the specified source of |
572 |
|
Iterator<? extends T> i = coll.iterator(); |
573 |
|
T candidate = i.next(); |
574 |
|
|
575 |
< |
while(i.hasNext()) { |
575 |
> |
while (i.hasNext()) { |
576 |
|
T next = i.next(); |
577 |
|
if (next.compareTo(candidate) < 0) |
578 |
|
candidate = next; |
609 |
|
Iterator<? extends T> i = coll.iterator(); |
610 |
|
T candidate = i.next(); |
611 |
|
|
612 |
< |
while(i.hasNext()) { |
612 |
> |
while (i.hasNext()) { |
613 |
|
T next = i.next(); |
614 |
|
if (comp.compare(next, candidate) < 0) |
615 |
|
candidate = next; |
642 |
|
Iterator<? extends T> i = coll.iterator(); |
643 |
|
T candidate = i.next(); |
644 |
|
|
645 |
< |
while(i.hasNext()) { |
645 |
> |
while (i.hasNext()) { |
646 |
|
T next = i.next(); |
647 |
|
if (next.compareTo(candidate) > 0) |
648 |
|
candidate = next; |
679 |
|
Iterator<? extends T> i = coll.iterator(); |
680 |
|
T candidate = i.next(); |
681 |
|
|
682 |
< |
while(i.hasNext()) { |
682 |
> |
while (i.hasNext()) { |
683 |
|
T next = i.next(); |
684 |
|
if (comp.compare(next, candidate) > 0) |
685 |
|
candidate = next; |
715 |
|
* Collections.rotate(l.subList(1, 4), -1); |
716 |
|
* </pre> |
717 |
|
* The resulting list is <tt>[a, c, d, b, e]</tt>. |
718 |
< |
* |
718 |
> |
* |
719 |
|
* <p>To move more than one element forward, increase the absolute value |
720 |
|
* of the rotation distance. To move elements backward, use a positive |
721 |
|
* shift distance. |
739 |
|
* constraints on this value; it may be zero, negative, or |
740 |
|
* greater than <tt>list.size()</tt>. |
741 |
|
* @throws UnsupportedOperationException if the specified list or |
742 |
< |
* its list-iterator does not support the <tt>set</tt> method. |
742 |
> |
* its list-iterator does not support the <tt>set</tt> operation. |
743 |
|
* @since 1.4 |
744 |
|
*/ |
745 |
|
public static void rotate(List<?> list, int distance) { |
775 |
|
private static void rotate2(List<?> list, int distance) { |
776 |
|
int size = list.size(); |
777 |
|
if (size == 0) |
778 |
< |
return; |
778 |
> |
return; |
779 |
|
int mid = -distance % size; |
780 |
|
if (mid < 0) |
781 |
|
mid += size; |
802 |
|
* <tt>e</tt> such that |
803 |
|
* <tt>(oldVal==null ? e==null : oldVal.equals(e))</tt>. |
804 |
|
* @throws UnsupportedOperationException if the specified list or |
805 |
< |
* its list-iterator does not support the <tt>set</tt> method. |
805 |
> |
* its list-iterator does not support the <tt>set</tt> operation. |
806 |
|
* @since 1.4 |
807 |
|
*/ |
808 |
|
public static <T> boolean replaceAll(List<T> list, T oldVal, T newVal) { |
973 |
|
* that the backing collection is a set or a list.<p> |
974 |
|
* |
975 |
|
* The returned collection will be serializable if the specified collection |
976 |
< |
* is serializable. |
976 |
> |
* is serializable. |
977 |
|
* |
978 |
|
* @param c the collection for which an unmodifiable view is to be |
979 |
|
* returned. |
1017 |
|
}; |
1018 |
|
} |
1019 |
|
|
1020 |
< |
public boolean add(E o){ |
1020 |
> |
public boolean add(E e){ |
1021 |
|
throw new UnsupportedOperationException(); |
1022 |
|
} |
1023 |
|
public boolean remove(Object o) { |
1049 |
|
* iterator, result in an <tt>UnsupportedOperationException</tt>.<p> |
1050 |
|
* |
1051 |
|
* The returned set will be serializable if the specified set |
1052 |
< |
* is serializable. |
1052 |
> |
* is serializable. |
1053 |
|
* |
1054 |
|
* @param s the set for which an unmodifiable view is to be returned. |
1055 |
|
* @return an unmodifiable view of the specified set. |
1056 |
|
*/ |
1054 |
– |
|
1057 |
|
public static <T> Set<T> unmodifiableSet(Set<? extends T> s) { |
1058 |
|
return new UnmodifiableSet<T>(s); |
1059 |
|
} |
1080 |
|
* an <tt>UnsupportedOperationException</tt>.<p> |
1081 |
|
* |
1082 |
|
* The returned sorted set will be serializable if the specified sorted set |
1083 |
< |
* is serializable. |
1083 |
> |
* is serializable. |
1084 |
|
* |
1085 |
|
* @param s the sorted set for which an unmodifiable view is to be |
1086 |
< |
* returned. |
1086 |
> |
* returned. |
1087 |
|
* @return an unmodifiable view of the specified sorted set. |
1088 |
|
*/ |
1089 |
|
public static <T> SortedSet<T> unmodifiableSortedSet(SortedSet<T> s) { |
1185 |
|
public void remove() { |
1186 |
|
throw new UnsupportedOperationException(); |
1187 |
|
} |
1188 |
< |
public void set(E o) { |
1188 |
> |
public void set(E e) { |
1189 |
|
throw new UnsupportedOperationException(); |
1190 |
|
} |
1191 |
< |
public void add(E o) { |
1191 |
> |
public void add(E e) { |
1192 |
|
throw new UnsupportedOperationException(); |
1193 |
|
} |
1194 |
|
}; |
1254 |
|
* <tt>UnsupportedOperationException</tt>.<p> |
1255 |
|
* |
1256 |
|
* The returned map will be serializable if the specified map |
1257 |
< |
* is serializable. |
1257 |
> |
* is serializable. |
1258 |
|
* |
1259 |
|
* @param m the map for which an unmodifiable view is to be returned. |
1260 |
|
* @return an unmodifiable view of the specified map. |
1290 |
|
public V remove(Object key) { |
1291 |
|
throw new UnsupportedOperationException(); |
1292 |
|
} |
1293 |
< |
public void putAll(Map<? extends K, ? extends V> t) { |
1293 |
> |
public void putAll(Map<? extends K, ? extends V> m) { |
1294 |
|
throw new UnsupportedOperationException(); |
1295 |
|
} |
1296 |
|
public void clear() { |
1336 |
|
private static final long serialVersionUID = 7854390611657943733L; |
1337 |
|
|
1338 |
|
UnmodifiableEntrySet(Set<? extends Map.Entry<? extends K, ? extends V>> s) { |
1339 |
< |
super((Set<Map.Entry<K,V>>)(Set)s); |
1339 |
> |
super((Set)s); |
1340 |
|
} |
1341 |
|
public Iterator<Map.Entry<K,V>> iterator() { |
1342 |
|
return new Iterator<Map.Entry<K,V>>() { |
1365 |
|
// We don't pass a to c.toArray, to avoid window of |
1366 |
|
// vulnerability wherein an unscrupulous multithreaded client |
1367 |
|
// could get his hands on raw (unwrapped) Entries from c. |
1368 |
< |
Object[] arr = |
1367 |
< |
c.toArray( |
1368 |
< |
a.length==0 ? a : |
1369 |
< |
(T[])java.lang.reflect.Array.newInstance(a.getClass().getComponentType(), 0)); |
1368 |
> |
Object[] arr = c.toArray(a.length==0 ? a : Arrays.copyOf(a, 0)); |
1369 |
|
|
1370 |
|
for (int i=0; i<arr.length; i++) |
1371 |
|
arr[i] = new UnmodifiableEntry<K,V>((Map.Entry<K,V>)arr[i]); |
1455 |
|
* an <tt>UnsupportedOperationException</tt>.<p> |
1456 |
|
* |
1457 |
|
* The returned sorted map will be serializable if the specified sorted map |
1458 |
< |
* is serializable. |
1458 |
> |
* is serializable. |
1459 |
|
* |
1460 |
|
* @param m the sorted map for which an unmodifiable view is to be |
1461 |
< |
* returned. |
1461 |
> |
* returned. |
1462 |
|
* @return an unmodifiable view of the specified sorted map. |
1463 |
|
*/ |
1464 |
|
public static <K,V> SortedMap<K,V> unmodifiableSortedMap(SortedMap<K, ? extends V> m) { |
1522 |
|
* that the backing collection is a set or a list.<p> |
1523 |
|
* |
1524 |
|
* The returned collection will be serializable if the specified collection |
1525 |
< |
* is serializable. |
1525 |
> |
* is serializable. |
1526 |
|
* |
1527 |
|
* @param c the collection to be "wrapped" in a synchronized collection. |
1528 |
|
* @return a synchronized view of the specified collection. |
1576 |
|
return c.iterator(); // Must be manually synched by user! |
1577 |
|
} |
1578 |
|
|
1579 |
< |
public boolean add(E o) { |
1580 |
< |
synchronized(mutex) {return c.add(o);} |
1579 |
> |
public boolean add(E e) { |
1580 |
> |
synchronized(mutex) {return c.add(e);} |
1581 |
|
} |
1582 |
|
public boolean remove(Object o) { |
1583 |
|
synchronized(mutex) {return c.remove(o);} |
1672 |
|
* sorted set when iterating over it or any of its <tt>subSet</tt>, |
1673 |
|
* <tt>headSet</tt>, or <tt>tailSet</tt> views. |
1674 |
|
* <pre> |
1675 |
< |
* SortedSet s = Collections.synchronizedSortedSet(new HashSortedSet()); |
1675 |
> |
* SortedSet s = Collections.synchronizedSortedSet(new TreeSet()); |
1676 |
|
* ... |
1677 |
|
* synchronized(s) { |
1678 |
|
* Iterator i = s.iterator(); // Must be in the synchronized block |
1682 |
|
* </pre> |
1683 |
|
* or: |
1684 |
|
* <pre> |
1685 |
< |
* SortedSet s = Collections.synchronizedSortedSet(new HashSortedSet()); |
1685 |
> |
* SortedSet s = Collections.synchronizedSortedSet(new TreeSet()); |
1686 |
|
* SortedSet s2 = s.headSet(foo); |
1687 |
|
* ... |
1688 |
|
* synchronized(s) { // Note: s, not s2!!! |
2006 |
|
public Set<Map.Entry<K,V>> entrySet() { |
2007 |
|
synchronized(mutex) { |
2008 |
|
if (entrySet==null) |
2009 |
< |
entrySet = new SynchronizedSet<Map.Entry<K,V>>((Set<Map.Entry<K,V>>)m.entrySet(), mutex); |
2009 |
> |
entrySet = new SynchronizedSet<Map.Entry<K,V>>(m.entrySet(), mutex); |
2010 |
|
return entrySet; |
2011 |
|
} |
2012 |
|
} |
2044 |
|
* collections views of any of its <tt>subMap</tt>, <tt>headMap</tt> or |
2045 |
|
* <tt>tailMap</tt> views. |
2046 |
|
* <pre> |
2047 |
< |
* SortedMap m = Collections.synchronizedSortedMap(new HashSortedMap()); |
2047 |
> |
* SortedMap m = Collections.synchronizedSortedMap(new TreeMap()); |
2048 |
|
* ... |
2049 |
|
* Set s = m.keySet(); // Needn't be in synchronized block |
2050 |
|
* ... |
2056 |
|
* </pre> |
2057 |
|
* or: |
2058 |
|
* <pre> |
2059 |
< |
* SortedMap m = Collections.synchronizedSortedMap(new HashSortedMap()); |
2059 |
> |
* SortedMap m = Collections.synchronizedSortedMap(new TreeMap()); |
2060 |
|
* SortedMap m2 = m.subMap(foo, bar); |
2061 |
|
* ... |
2062 |
|
* Set s2 = m2.keySet(); // Needn't be in synchronized block |
2190 |
|
Class<E> type) { |
2191 |
|
return new CheckedCollection<E>(c, type); |
2192 |
|
} |
2193 |
< |
|
2193 |
> |
|
2194 |
|
/** |
2195 |
|
* @serial include |
2196 |
|
*/ |
2220 |
|
public Object[] toArray() { return c.toArray(); } |
2221 |
|
public <T> T[] toArray(T[] a) { return c.toArray(a); } |
2222 |
|
public String toString() { return c.toString(); } |
2224 |
– |
public Iterator<E> iterator() { return c.iterator(); } |
2223 |
|
public boolean remove(Object o) { return c.remove(o); } |
2224 |
|
public boolean containsAll(Collection<?> coll) { |
2225 |
|
return c.containsAll(coll); |
2234 |
|
c.clear(); |
2235 |
|
} |
2236 |
|
|
2237 |
< |
public boolean add(E o){ |
2238 |
< |
typeCheck(o); |
2239 |
< |
return c.add(o); |
2237 |
> |
public Iterator<E> iterator() { |
2238 |
> |
return new Iterator<E>() { |
2239 |
> |
private final Iterator<E> it = c.iterator(); |
2240 |
> |
public boolean hasNext() { return it.hasNext(); } |
2241 |
> |
public E next() { return it.next(); } |
2242 |
> |
public void remove() { it.remove(); }}; |
2243 |
> |
} |
2244 |
> |
|
2245 |
> |
public boolean add(E e){ |
2246 |
> |
typeCheck(e); |
2247 |
> |
return c.add(e); |
2248 |
|
} |
2249 |
|
|
2250 |
|
public boolean addAll(Collection<? extends E> coll) { |
2252 |
|
* Dump coll into an array of the required type. This serves |
2253 |
|
* three purposes: it insulates us from concurrent changes in |
2254 |
|
* the contents of coll, it type-checks all of the elements in |
2255 |
< |
* coll, and it provides all-or-nothing semantics(which we |
2255 |
> |
* coll, and it provides all-or-nothing semantics (which we |
2256 |
|
* wouldn't get if we type-checked each element as we added it). |
2257 |
|
*/ |
2258 |
|
E[] a = null; |
2259 |
|
try { |
2260 |
|
a = coll.toArray(zeroLengthElementArray()); |
2261 |
< |
} catch(ArrayStoreException e) { |
2261 |
> |
} catch (ArrayStoreException e) { |
2262 |
|
throw new ClassCastException(); |
2263 |
|
} |
2264 |
|
|
2271 |
|
private E[] zeroLengthElementArray = null; // Lazily initialized |
2272 |
|
|
2273 |
|
/* |
2274 |
< |
* We don't need locking or volatile, because it's OK if we create |
2274 |
> |
* We don't need locking or volatile, because it's OK if we create |
2275 |
|
* several zeroLengthElementArrays, and they're immutable. |
2276 |
|
*/ |
2277 |
|
E[] zeroLengthElementArray() { |
2306 |
|
public static <E> Set<E> checkedSet(Set<E> s, Class<E> type) { |
2307 |
|
return new CheckedSet<E>(s, type); |
2308 |
|
} |
2309 |
< |
|
2309 |
> |
|
2310 |
|
/** |
2311 |
|
* @serial include |
2312 |
|
*/ |
2442 |
|
E[] a = null; |
2443 |
|
try { |
2444 |
|
a = c.toArray(zeroLengthElementArray()); |
2445 |
< |
} catch(ArrayStoreException e) { |
2445 |
> |
} catch (ArrayStoreException e) { |
2446 |
|
throw new ClassCastException(); |
2447 |
|
} |
2448 |
|
|
2462 |
|
public int previousIndex() { return i.previousIndex(); } |
2463 |
|
public void remove() { i.remove(); } |
2464 |
|
|
2465 |
< |
public void set(E o) { |
2466 |
< |
typeCheck(o); |
2467 |
< |
i.set(o); |
2465 |
> |
public void set(E e) { |
2466 |
> |
typeCheck(e); |
2467 |
> |
i.set(e); |
2468 |
|
} |
2469 |
|
|
2470 |
< |
public void add(E o) { |
2471 |
< |
typeCheck(o); |
2472 |
< |
i.add(o); |
2470 |
> |
public void add(E e) { |
2471 |
> |
typeCheck(e); |
2472 |
> |
i.add(e); |
2473 |
|
} |
2474 |
|
}; |
2475 |
|
} |
2588 |
|
K[] keys = null; |
2589 |
|
try { |
2590 |
|
keys = t.keySet().toArray(zeroLengthKeyArray()); |
2591 |
< |
} catch(ArrayStoreException e) { |
2591 |
> |
} catch (ArrayStoreException e) { |
2592 |
|
throw new ClassCastException(); |
2593 |
|
} |
2594 |
|
V[] values = null; |
2595 |
|
try { |
2596 |
|
values = t.values().toArray(zeroLengthValueArray()); |
2597 |
< |
} catch(ArrayStoreException e) { |
2597 |
> |
} catch (ArrayStoreException e) { |
2598 |
|
throw new ClassCastException(); |
2599 |
|
} |
2600 |
|
|
2610 |
|
private V[] zeroLengthValueArray = null; |
2611 |
|
|
2612 |
|
/* |
2613 |
< |
* We don't need locking or volatile, because it's OK if we create |
2613 |
> |
* We don't need locking or volatile, because it's OK if we create |
2614 |
|
* several zeroLengthValueArrays, and they're immutable. |
2615 |
|
*/ |
2616 |
|
private K[] zeroLengthKeyArray() { |
2664 |
|
s.clear(); |
2665 |
|
} |
2666 |
|
|
2667 |
< |
public boolean add(Map.Entry<K, V> o){ |
2667 |
> |
public boolean add(Map.Entry<K, V> e){ |
2668 |
|
throw new UnsupportedOperationException(); |
2669 |
|
} |
2670 |
|
public boolean addAll(Collection<? extends Map.Entry<K, V>> coll) { |
2706 |
|
// We don't pass a to s.toArray, to avoid window of |
2707 |
|
// vulnerability wherein an unscrupulous multithreaded client |
2708 |
|
// could get his hands on raw (unwrapped) Entries from s. |
2709 |
< |
Object[] arr = s.toArray(a.length==0 ? a : |
2704 |
< |
(T[])Array.newInstance(a.getClass().getComponentType(), 0)); |
2709 |
> |
Object[] arr = s.toArray(a.length==0 ? a : Arrays.copyOf(a, 0)); |
2710 |
|
|
2711 |
|
for (int i=0; i<arr.length; i++) |
2712 |
|
arr[i] = new CheckedEntry<K,V>((Map.Entry<K,V>)arr[i], |
3065 |
|
|
3066 |
|
final private E element; |
3067 |
|
|
3068 |
< |
SingletonSet(E o) {element = o;} |
3068 |
> |
SingletonSet(E e) {element = e;} |
3069 |
|
|
3070 |
|
public Iterator<E> iterator() { |
3071 |
|
return new Iterator<E>() { |
3173 |
|
|
3174 |
|
public Set<Map.Entry<K,V>> entrySet() { |
3175 |
|
if (entrySet==null) |
3176 |
< |
entrySet = singleton((Map.Entry<K,V>)new ImmutableEntry<K,V>(k, v)); |
3176 |
> |
entrySet = Collections.<Map.Entry<K,V>>singleton( |
3177 |
> |
new SimpleImmutableEntry<K,V>(k, v)); |
3178 |
|
return entrySet; |
3179 |
|
} |
3180 |
|
|
3184 |
|
return values; |
3185 |
|
} |
3186 |
|
|
3181 |
– |
private static class ImmutableEntry<K,V> |
3182 |
– |
implements Map.Entry<K,V> { |
3183 |
– |
final K k; |
3184 |
– |
final V v; |
3185 |
– |
|
3186 |
– |
ImmutableEntry(K key, V value) { |
3187 |
– |
k = key; |
3188 |
– |
v = value; |
3189 |
– |
} |
3190 |
– |
|
3191 |
– |
public K getKey() {return k;} |
3192 |
– |
|
3193 |
– |
public V getValue() {return v;} |
3194 |
– |
|
3195 |
– |
public V setValue(V value) { |
3196 |
– |
throw new UnsupportedOperationException(); |
3197 |
– |
} |
3198 |
– |
|
3199 |
– |
public boolean equals(Object o) { |
3200 |
– |
if (!(o instanceof Map.Entry)) |
3201 |
– |
return false; |
3202 |
– |
Map.Entry e = (Map.Entry)o; |
3203 |
– |
return eq(e.getKey(), k) && eq(e.getValue(), v); |
3204 |
– |
} |
3205 |
– |
|
3206 |
– |
public int hashCode() { |
3207 |
– |
return ((k==null ? 0 : k.hashCode()) ^ |
3208 |
– |
(v==null ? 0 : v.hashCode())); |
3209 |
– |
} |
3210 |
– |
|
3211 |
– |
public String toString() { |
3212 |
– |
return k+"="+v; |
3213 |
– |
} |
3214 |
– |
} |
3187 |
|
} |
3188 |
|
|
3189 |
|
/** |
3202 |
|
* @see List#addAll(int, Collection) |
3203 |
|
*/ |
3204 |
|
public static <T> List<T> nCopies(int n, T o) { |
3205 |
+ |
if (n < 0) |
3206 |
+ |
throw new IllegalArgumentException("List length = " + n); |
3207 |
|
return new CopiesList<T>(n, o); |
3208 |
|
} |
3209 |
|
|
3216 |
|
{ |
3217 |
|
static final long serialVersionUID = 2739099268398711800L; |
3218 |
|
|
3219 |
< |
int n; |
3220 |
< |
E element; |
3219 |
> |
final int n; |
3220 |
> |
final E element; |
3221 |
|
|
3222 |
< |
CopiesList(int n, E o) { |
3223 |
< |
if (n < 0) |
3250 |
< |
throw new IllegalArgumentException("List length = " + n); |
3222 |
> |
CopiesList(int n, E e) { |
3223 |
> |
assert n >= 0; |
3224 |
|
this.n = n; |
3225 |
< |
element = o; |
3225 |
> |
element = e; |
3226 |
|
} |
3227 |
|
|
3228 |
|
public int size() { |
3233 |
|
return n != 0 && eq(obj, element); |
3234 |
|
} |
3235 |
|
|
3236 |
+ |
public int indexOf(Object o) { |
3237 |
+ |
return contains(o) ? 0 : -1; |
3238 |
+ |
} |
3239 |
+ |
|
3240 |
+ |
public int lastIndexOf(Object o) { |
3241 |
+ |
return contains(o) ? n - 1 : -1; |
3242 |
+ |
} |
3243 |
+ |
|
3244 |
|
public E get(int index) { |
3245 |
< |
if (index<0 || index>=n) |
3245 |
> |
if (index < 0 || index >= n) |
3246 |
|
throw new IndexOutOfBoundsException("Index: "+index+ |
3247 |
|
", Size: "+n); |
3248 |
|
return element; |
3249 |
|
} |
3250 |
+ |
|
3251 |
+ |
public Object[] toArray() { |
3252 |
+ |
final Object[] a = new Object[n]; |
3253 |
+ |
if (element != null) |
3254 |
+ |
Arrays.fill(a, 0, n, element); |
3255 |
+ |
return a; |
3256 |
+ |
} |
3257 |
+ |
|
3258 |
+ |
public <T> T[] toArray(T[] a) { |
3259 |
+ |
final int n = this.n; |
3260 |
+ |
if (a.length < n) { |
3261 |
+ |
a = (T[])java.lang.reflect.Array |
3262 |
+ |
.newInstance(a.getClass().getComponentType(), n); |
3263 |
+ |
if (element != null) |
3264 |
+ |
Arrays.fill(a, 0, n, element); |
3265 |
+ |
} else { |
3266 |
+ |
Arrays.fill(a, 0, n, element); |
3267 |
+ |
if (a.length > n) |
3268 |
+ |
a[n] = null; |
3269 |
+ |
} |
3270 |
+ |
return a; |
3271 |
+ |
} |
3272 |
+ |
|
3273 |
+ |
public List<E> subList(int fromIndex, int toIndex) { |
3274 |
+ |
if (fromIndex < 0) |
3275 |
+ |
throw new IndexOutOfBoundsException("fromIndex = " + fromIndex); |
3276 |
+ |
if (toIndex > n) |
3277 |
+ |
throw new IndexOutOfBoundsException("toIndex = " + toIndex); |
3278 |
+ |
if (fromIndex > toIndex) |
3279 |
+ |
throw new IllegalArgumentException("fromIndex(" + fromIndex + |
3280 |
+ |
") > toIndex(" + toIndex + ")"); |
3281 |
+ |
return new CopiesList(toIndex - fromIndex, element); |
3282 |
+ |
} |
3283 |
|
} |
3284 |
|
|
3285 |
|
/** |
3338 |
|
public static <T> Comparator<T> reverseOrder(Comparator<T> cmp) { |
3339 |
|
if (cmp == null) |
3340 |
|
return new ReverseComparator(); // Unchecked warning!! |
3341 |
< |
|
3341 |
> |
|
3342 |
|
return new ReverseComparator2<T>(cmp); |
3343 |
|
} |
3344 |
< |
|
3344 |
> |
|
3345 |
|
/** |
3346 |
|
* @serial include |
3347 |
|
*/ |
3349 |
|
Serializable |
3350 |
|
{ |
3351 |
|
private static final long serialVersionUID = 4374092139857L; |
3352 |
< |
|
3352 |
> |
|
3353 |
|
/** |
3354 |
|
* The comparator specified in the static factory. This will never |
3355 |
|
* be null, as the static factory returns a ReverseComparator |
3358 |
|
* @serial |
3359 |
|
*/ |
3360 |
|
private Comparator<T> cmp; |
3361 |
< |
|
3361 |
> |
|
3362 |
|
ReverseComparator2(Comparator<T> cmp) { |
3363 |
|
assert cmp != null; |
3364 |
|
this.cmp = cmp; |
3365 |
|
} |
3366 |
< |
|
3366 |
> |
|
3367 |
|
public int compare(T t1, T t2) { |
3368 |
|
return cmp.compare(t2, t1); |
3369 |
|
} |
3483 |
|
c1 = c2; |
3484 |
|
c2 = tmp; |
3485 |
|
} |
3486 |
< |
|
3486 |
> |
|
3487 |
|
for (Object e : c1) |
3488 |
|
if (c2.contains(e)) |
3489 |
|
return false; |
3504 |
|
* </pre> |
3505 |
|
* |
3506 |
|
* @param c the collection into which <tt>elements</tt> are to be inserted |
3507 |
< |
* @param a the elements to insert into <tt>c</tt> |
3507 |
> |
* @param elements the elements to insert into <tt>c</tt> |
3508 |
|
* @return <tt>true</tt> if the collection changed as a result of the call |
3509 |
|
* @throws UnsupportedOperationException if <tt>c</tt> does not support |
3510 |
< |
* the <tt>add</tt> method |
3510 |
> |
* the <tt>add</tt> operation |
3511 |
|
* @throws NullPointerException if <tt>elements</tt> contains one or more |
3512 |
< |
* null values and <tt>c</tt> does not support null elements, or |
3512 |
> |
* null values and <tt>c</tt> does not permit null elements, or |
3513 |
|
* if <tt>c</tt> or <tt>elements</tt> are <tt>null</tt> |
3514 |
< |
* @throws IllegalArgumentException if some aspect of a value in |
3514 |
> |
* @throws IllegalArgumentException if some property of a value in |
3515 |
|
* <tt>elements</tt> prevents it from being added to <tt>c</tt> |
3516 |
|
* @see Collection#addAll(Collection) |
3517 |
|
* @since 1.5 |
3518 |
|
*/ |
3519 |
< |
public static <T> boolean addAll(Collection<? super T> c, T... a) { |
3519 |
> |
public static <T> boolean addAll(Collection<? super T> c, T... elements) { |
3520 |
|
boolean result = false; |
3521 |
< |
for (T e : a) |
3522 |
< |
result |= c.add(e); |
3521 |
> |
for (T element : elements) |
3522 |
> |
result |= c.add(element); |
3523 |
|
return result; |
3524 |
|
} |
3525 |
|
|
3543 |
|
* to this method, and no reference to the map is retained, as illustrated |
3544 |
|
* in the following code fragment: |
3545 |
|
* <pre> |
3546 |
< |
* Set<Object> weakHashSet = Collections.asSet( |
3546 |
> |
* Set<Object> weakHashSet = Collections.newSetFromMap( |
3547 |
|
* new WeakHashMap<Object, Boolean>()); |
3548 |
|
* </pre> |
3549 |
|
* |
3550 |
|
* @param map the backing map |
3551 |
|
* @return the set backed by the map |
3552 |
|
* @throws IllegalArgumentException if <tt>map</tt> is not empty |
3553 |
+ |
* @since 1.6 |
3554 |
|
*/ |
3555 |
< |
public static <E> Set<E> asSet(Map<E, Boolean> map) { |
3556 |
< |
return new MapAsSet<E>(map); |
3555 |
> |
public static <E> Set<E> newSetFromMap(Map<E, Boolean> map) { |
3556 |
> |
return new SetFromMap<E>(map); |
3557 |
|
} |
3558 |
|
|
3559 |
< |
private static class MapAsSet<E> extends AbstractSet<E> |
3559 |
> |
private static class SetFromMap<E> extends AbstractSet<E> |
3560 |
|
implements Set<E>, Serializable |
3561 |
|
{ |
3562 |
|
private final Map<E, Boolean> m; // The backing map |
3563 |
|
private transient Set<E> keySet; // Its keySet |
3564 |
|
|
3565 |
< |
MapAsSet(Map<E, Boolean> map) { |
3565 |
> |
SetFromMap(Map<E, Boolean> map) { |
3566 |
|
if (!map.isEmpty()) |
3567 |
|
throw new IllegalArgumentException("Map is non-empty"); |
3568 |
|
m = map; |
3606 |
|
* <tt>remove</tt> is mapped to <tt>pop</tt> and so on. This |
3607 |
|
* view can be useful when you would like to use a method |
3608 |
|
* requiring a <tt>Queue</tt> but you need Lifo ordering. |
3609 |
< |
* @param deque the Deque |
3609 |
> |
* |
3610 |
> |
* @param deque the deque |
3611 |
|
* @return the queue |
3612 |
|
* @since 1.6 |
3613 |
|
*/ |
3615 |
|
return new AsLIFOQueue<T>(deque); |
3616 |
|
} |
3617 |
|
|
3618 |
< |
static class AsLIFOQueue<E> extends AbstractQueue<E> |
3618 |
> |
static class AsLIFOQueue<E> extends AbstractQueue<E> |
3619 |
|
implements Queue<E>, Serializable { |
3620 |
+ |
private static final long serialVersionUID = 1802017725587941708L; |
3621 |
|
private final Deque<E> q; |
3622 |
|
AsLIFOQueue(Deque<E> q) { this.q = q; } |
3623 |
< |
public boolean offer(E o) { return q.offerFirst(o); } |
3623 |
> |
public boolean add(E e) { q.addFirst(e); return true; } |
3624 |
> |
public boolean offer(E e) { return q.offerFirst(e); } |
3625 |
|
public E poll() { return q.pollFirst(); } |
3626 |
|
public E remove() { return q.removeFirst(); } |
3627 |
|
public E peek() { return q.peekFirst(); } |
3632 |
|
public Iterator<E> iterator() { return q.iterator(); } |
3633 |
|
public Object[] toArray() { return q.toArray(); } |
3634 |
|
public <T> T[] toArray(T[] a) { return q.toArray(a); } |
3617 |
– |
public boolean add(E o) { return q.offerFirst(o); } |
3635 |
|
public boolean remove(Object o) { return q.remove(o); } |
3636 |
|
public void clear() { q.clear(); } |
3637 |
|
} |