ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/jsr166/jsr166/src/main/java/util/concurrent/ConcurrentHashMap.java
Revision: 1.3
Committed: Thu May 29 13:49:24 2003 UTC (21 years ago) by dl
Branch: MAIN
CVS Tags: JSR166_PRERELEASE_0_1
Changes since 1.2: +40 -2 lines
Log Message:
Please the new generics compiler

File Contents

# Content
1 /*
2 * Written by Doug Lea with assistance from members of JCP JSR-166
3 * Expert Group and released to the public domain. Use, modify, and
4 * redistribute this code in any way without acknowledgement.
5 */
6
7 package java.util.concurrent;
8
9 import java.util.*;
10 import java.io.Serializable;
11 import java.io.IOException;
12 import java.io.ObjectInputStream;
13 import java.io.ObjectOutputStream;
14
15 /**
16 * A version of Hashtable supporting
17 * concurrency for both retrievals and updates.
18 *
19 * <dl>
20 * <dt> Retrievals
21 *
22 * <dd> Retrievals may overlap updates. Successful retrievals using
23 * get(key) and containsKey(key) usually run without
24 * locking. Unsuccessful retrievals (i.e., when the key is not
25 * present) do involve brief locking. Because
26 * retrieval operations can ordinarily overlap with update operations
27 * (i.e., put, remove, and their derivatives), retrievals can only be
28 * guaranteed to return the results of the most recently
29 * <em>completed</em> operations holding upon their onset. Retrieval
30 * operations may or may not return results reflecting in-progress
31 * writing operations. However, the retrieval operations do always
32 * return consistent results -- either those holding before any single
33 * modification or after it, but never a nonsense result. For
34 * aggregate operations such as putAll and clear, concurrent reads may
35 * reflect insertion or removal of only some entries. <p>
36 *
37 * Iterators and Enumerations (i.e., those returned by
38 * keySet().iterator(), entrySet().iterator(), values().iterator(),
39 * keys(), and elements()) return elements reflecting the state of the
40 * hash table at some point at or since the creation of the
41 * iterator/enumeration. They will return at most one instance of
42 * each element (via next()/nextElement()), but might or might not
43 * reflect puts and removes that have been processed since
44 * construction if the Iterator. They do <em>not</em> throw
45 * ConcurrentModificationException. However, these iterators are
46 * designed to be used by only one thread at a time. Passing an
47 * iterator across multiple threads may lead to unpredictable traversal
48 * if the table is being concurrently modified. <p>
49 *
50 *
51 * <dt> Updates
52 *
53 * <dd> This class supports a hard-wired preset <em>concurrency
54 * level</em> of 32. This allows a maximum of 32 put and/or remove
55 * operations to proceed concurrently. This level is an upper bound on
56 * concurrency, not a guarantee, since it interacts with how
57 * well-strewn elements are across bins of the table. (The preset
58 * value in part reflects the fact that even on large multiprocessors,
59 * factors other than synchronization tend to be bottlenecks when more
60 * than 32 threads concurrently attempt updates.)
61 * Additionally, operations triggering internal resizing and clearing
62 * do not execute concurrently with any operation.
63 * <p>
64 *
65 * There is <em>NOT</em> any support for locking the entire table to
66 * prevent updates.
67 *
68 * </dl>
69 *
70 *
71 * This class may be used as a direct replacement for
72 * java.util.Hashtable in any application that does not rely
73 * on the ability to lock the entire table to prevent updates.
74 * Like Hashtable but unlike java.util.HashMap,
75 * this class does NOT allow <tt>null</tt> to be used as a key or
76 * value.
77 * <p>
78 *
79 **/
80 public class ConcurrentHashMap<K, V> extends AbstractMap<K, V>
81 implements ConcurrentMap<K, V>, Cloneable, Serializable {
82
83 /*
84 The basic strategy is an optimistic-style scheme based on
85 the guarantee that the hash table and its lists are always
86 kept in a consistent enough state to be read without locking:
87
88 * Read operations first proceed without locking, by traversing the
89 apparently correct list of the apparently correct bin. If an
90 entry is found, but not invalidated (value field null), it is
91 returned. If not found, operations must recheck (after a memory
92 barrier) to make sure they are using both the right list and
93 the right table (which can change under resizes). If
94 invalidated, reads must acquire main update lock to wait out
95 the update, and then re-traverse.
96
97 * All list additions are at the front of each bin, making it easy
98 to check changes, and also fast to traverse. Entry next
99 pointers are never assigned. Remove() builds new nodes when
100 necessary to preserve this.
101
102 * Remove() (also clear()) invalidates removed nodes to alert read
103 operations that they must wait out the full modifications.
104
105 * Locking for puts, removes (and, when necessary gets, etc)
106 is controlled by Segments, each covering a portion of the
107 table. During operations requiring global exclusivity (mainly
108 resize and clear), ALL of these locks are acquired at once.
109 Note that these segments are NOT contiguous -- they are based
110 on the least 5 bits of hashcodes. This ensures that the same
111 segment controls the same slots before and after resizing, which
112 is necessary for supporting concurrent retrievals. This
113 comes at the price of a mismatch of logical vs physical locality,
114 but this seems not to be a performance problem in practice.
115
116 */
117
118 /**
119 * The hash table data.
120 */
121 private transient Entry<K,V>[] table;
122
123
124 /**
125 * The number of concurrency control segments.
126 * The value can be at most 32 since ints are used
127 * as bitsets over segments. Emprically, it doesn't
128 * seem to pay to decrease it either, so the value should be at least 32.
129 * In other words, do not redefine this :-)
130 **/
131 private static final int CONCURRENCY_LEVEL = 32;
132
133 /**
134 * Mask value for indexing into segments
135 **/
136 private static final int SEGMENT_MASK = CONCURRENCY_LEVEL - 1;
137
138 /**
139 * Bookkeeping for each concurrency control segment.
140 * Each segment contains a local count of the number of
141 * elements in its region.
142 * However, the main use of a Segment is for its lock.
143 **/
144 private final static class Segment extends ReentrantLock {
145 /**
146 * The number of elements in this segment's region.
147 **/
148 private int count;
149
150 /**
151 * Get the count under synch.
152 **/
153 private int getCount() {
154 lock();
155 try {
156 return count;
157 }
158 finally {
159 unlock();
160 }
161 }
162
163 }
164
165 /**
166 * The array of concurrency control segments.
167 **/
168 private transient final Segment[] segments = new Segment[CONCURRENCY_LEVEL];
169
170
171 /**
172 * The default initial number of table slots for this table (32).
173 * Used when not otherwise specified in constructor.
174 **/
175 public static int DEFAULT_INITIAL_CAPACITY = 32;
176
177
178 /**
179 * The minimum capacity, used if a lower value is implicitly specified
180 * by either of the constructors with arguments.
181 * MUST be a power of two.
182 */
183 private static final int MINIMUM_CAPACITY = 32;
184
185 /**
186 * The maximum capacity, used if a higher value is implicitly specified
187 * by either of the constructors with arguments.
188 * MUST be a power of two <= 1<<30.
189 */
190 private static final int MAXIMUM_CAPACITY = 1 << 30;
191
192 /**
193 * The default load factor for this table (0.75)
194 * Used when not otherwise specified in constructor.
195 **/
196 public static final float DEFAULT_LOAD_FACTOR = 0.75f;
197
198 /**
199 * The load factor for the hash table.
200 *
201 * @serial
202 */
203 private final float loadFactor;
204
205 /**
206 * Per-segment resize threshold.
207 *
208 * @serial
209 */
210 private int threshold;
211
212
213 /**
214 * Number of segments voting for resize. The table is
215 * doubled when 1/4 of the segments reach threshold.
216 * Volatile but updated without synch since this is just a heuristic.
217 **/
218 private transient volatile int votesForResize;
219
220
221 /**
222 * Return the number of set bits in w.
223 * For a derivation of this algorithm, see
224 * "Algorithms and data structures with applications to
225 * graphics and geometry", by Jurg Nievergelt and Klaus Hinrichs,
226 * Prentice Hall, 1993.
227 * See also notes by Torsten Sillke at
228 * http://www.mathematik.uni-bielefeld.de/~sillke/PROBLEMS/bitcount
229 **/
230 private static int bitcount(int w) {
231 w -= (0xaaaaaaaa & w) >>> 1;
232 w = (w & 0x33333333) + ((w >>> 2) & 0x33333333);
233 w = (w + (w >>> 4)) & 0x0f0f0f0f;
234 w += w >>> 8;
235 w += w >>> 16;
236 return w & 0xff;
237 }
238
239 /**
240 * Returns the appropriate capacity (power of two) for the specified
241 * initial capacity argument.
242 */
243 private int p2capacity(int initialCapacity) {
244 int cap = initialCapacity;
245
246 // Compute the appropriate capacity
247 int result;
248 if (cap > MAXIMUM_CAPACITY || cap < 0) {
249 result = MAXIMUM_CAPACITY;
250 } else {
251 result = MINIMUM_CAPACITY;
252 while (result < cap)
253 result <<= 1;
254 }
255 return result;
256 }
257
258 /**
259 * Return hash code for Object x. Since we are using power-of-two
260 * tables, it is worth the effort to improve hashcode via
261 * the same multiplicative scheme as used in IdentityHashMap.
262 */
263 private static int hash(Object x) {
264 int h = x.hashCode();
265 // Multiply by 127 (quickly, via shifts), and mix in some high
266 // bits to help guard against bunching of codes that are
267 // consecutive or equally spaced.
268 return ((h << 7) - h + (h >>> 9) + (h >>> 17));
269 }
270
271
272 /**
273 * Check for equality of non-null references x and y.
274 **/
275 private boolean eq(Object x, Object y) {
276 return x == y || x.equals(y);
277 }
278
279 /** Create table array and set the per-segment threshold **/
280 private Entry<K,V>[] newTable(int capacity) {
281 threshold = (int)(capacity * loadFactor / CONCURRENCY_LEVEL) + 1;
282 return new Entry<K,V>[capacity];
283 }
284
285 /**
286 * Constructs a new, empty map with the specified initial
287 * capacity and the specified load factor.
288 *
289 * @param initialCapacity the initial capacity.
290 * The actual initial capacity is rounded up to the nearest power of two.
291 * @param loadFactor the load factor threshold, used to control resizing.
292 * This value is used in an approximate way: When at least
293 * a quarter of the segments of the table reach per-segment threshold, or
294 * one of the segments itself exceeds overall threshold,
295 * the table is doubled.
296 * This will on average cause resizing when the table-wide
297 * load factor is slightly less than the threshold. If you'd like
298 * to avoid resizing, you can set this to a ridiculously large
299 * value.
300 * @throws IllegalArgumentException if the load factor is nonpositive.
301 */
302 public ConcurrentHashMap(int initialCapacity, float loadFactor) {
303 if (!(loadFactor > 0))
304 throw new IllegalArgumentException("Illegal Load factor: "+ loadFactor);
305 this.loadFactor = loadFactor;
306 for (int i = 0; i < segments.length; ++i)
307 segments[i] = new Segment();
308 int cap = p2capacity(initialCapacity);
309 table = newTable(cap);
310 }
311
312 /**
313 * Constructs a new, empty map with the specified initial
314 * capacity and default load factor.
315 *
316 * @param initialCapacity the initial capacity of the
317 * ConcurrentHashMap.
318 * @throws IllegalArgumentException if the initial maximum number
319 * of elements is less
320 * than zero.
321 */
322 public ConcurrentHashMap(int initialCapacity) {
323 this(initialCapacity, DEFAULT_LOAD_FACTOR);
324 }
325
326 /**
327 * Constructs a new, empty map with a default initial capacity
328 * and default load factor.
329 */
330 public ConcurrentHashMap() {
331 this(DEFAULT_INITIAL_CAPACITY, DEFAULT_LOAD_FACTOR);
332 }
333
334 /**
335 * Constructs a new map with the same mappings as the given map. The
336 * map is created with a capacity of twice the number of mappings in
337 * the given map or 32 (whichever is greater), and a default load factor.
338 */
339 public <A extends K, B extends V> ConcurrentHashMap(Map<A,B> t) {
340 this(Math.max((int) (t.size() / DEFAULT_LOAD_FACTOR) + 1,
341 MINIMUM_CAPACITY),
342 DEFAULT_LOAD_FACTOR);
343 putAll(t);
344 }
345
346 /**
347 * Returns the number of key-value mappings in this map.
348 *
349 * @return the number of key-value mappings in this map.
350 */
351 public int size() {
352 int c = 0;
353 for (int i = 0; i < segments.length; ++i)
354 c += segments[i].getCount();
355 return c;
356 }
357
358 /**
359 * Returns <tt>true</tt> if this map contains no key-value mappings.
360 *
361 * @return <tt>true</tt> if this map contains no key-value mappings.
362 */
363 public boolean isEmpty() {
364 for (int i = 0; i < segments.length; ++i)
365 if (segments[i].getCount() != 0)
366 return false;
367 return true;
368 }
369
370
371 /**
372 * Returns the value to which the specified key is mapped in this table.
373 *
374 * @param key a key in the table.
375 * @return the value to which the key is mapped in this table;
376 * <code>null</code> if the key is not mapped to any value in
377 * this table.
378 * @exception NullPointerException if the key is
379 * <code>null</code>.
380 * @see #put(Object, Object)
381 */
382 public V get(K key) {
383 int hash = hash(key); // throws null pointer exception if key null
384
385 // Try first without locking...
386 Entry<K,V>[] tab = table;
387 int index = hash & (tab.length - 1);
388 Entry<K,V> first = tab[index];
389 Entry<K,V> e;
390
391 for (e = first; e != null; e = e.next) {
392 if (e.hash == hash && eq(key, e.key)) {
393 V value = e.value;
394 if (value != null)
395 return value;
396 else
397 break;
398 }
399 }
400
401 // Recheck under synch if key apparently not there or interference
402 Segment seg = segments[hash & SEGMENT_MASK];
403 seg.lock();
404 try {
405 tab = table;
406 index = hash & (tab.length - 1);
407 Entry<K,V> newFirst = tab[index];
408 if (e != null || first != newFirst) {
409 for (e = newFirst; e != null; e = e.next) {
410 if (e.hash == hash && eq(key, e.key))
411 return e.value;
412 }
413 }
414 return null;
415 }
416 finally {
417 seg.unlock();
418 }
419 }
420
421 /**
422 * Tests if the specified object is a key in this table.
423 *
424 * @param key possible key.
425 * @return <code>true</code> if and only if the specified object
426 * is a key in this table, as determined by the
427 * <tt>equals</tt> method; <code>false</code> otherwise.
428 * @exception NullPointerException if the key is
429 * <code>null</code>.
430 * @see #contains(Object)
431 */
432 public boolean containsKey(Object key) {
433 // Annoyingly, for now, duplicate get, since can't call
434 // because different signatures.
435
436 int hash = hash(key); // throws null pointer exception if key null
437
438 // Try first without locking...
439 Entry<K,V>[] tab = table;
440 int index = hash & (tab.length - 1);
441 Entry<K,V> first = tab[index];
442 Entry<K,V> e;
443
444 for (e = first; e != null; e = e.next) {
445 if (e.hash == hash && eq(key, e.key)) {
446 V value = e.value;
447 if (value != null)
448 return true;
449 else
450 break;
451 }
452 }
453
454 // Recheck under synch if key apparently not there or interference
455 Segment seg = segments[hash & SEGMENT_MASK];
456 seg.lock();
457 try {
458 tab = table;
459 index = hash & (tab.length - 1);
460 Entry<K,V> newFirst = tab[index];
461 if (e != null || first != newFirst) {
462 for (e = newFirst; e != null; e = e.next) {
463 if (e.hash == hash && eq(key, e.key))
464 return true;
465 }
466 }
467 return false;
468 }
469 finally {
470 seg.unlock();
471 }
472 }
473
474
475 /**
476 * Maps the specified <code>key</code> to the specified
477 * <code>value</code> in this table. Neither the key nor the
478 * value can be <code>null</code>. (Note that this policy is
479 * the same as for java.util.Hashtable, but unlike java.util.HashMap,
480 * which does accept nulls as valid keys and values.)<p>
481 *
482 * The value can be retrieved by calling the <code>get</code> method
483 * with a key that is equal to the original key.
484 *
485 * @param key the table key.
486 * @param value the value.
487 * @return the previous value of the specified key in this table,
488 * or <code>null</code> if it did not have one.
489 * @exception NullPointerException if the key or value is
490 * <code>null</code>.
491 * @see Object#equals(Object)
492 * @see #get(Object)
493 */
494 public V put(K key, V value) {
495 if (value == null)
496 throw new NullPointerException();
497
498 int hash = hash(key);
499 Segment seg = segments[hash & SEGMENT_MASK];
500 int segcount;
501 Entry<K,V>[] tab;
502 int votes;
503
504 seg.lock();
505 try {
506 tab = table;
507 int index = hash & (tab.length-1);
508 Entry<K,V> first = tab[index];
509
510 for (Entry<K,V> e = first; e != null; e = e.next) {
511 if (e.hash == hash && eq(key, e.key)) {
512 V oldValue = e.value;
513 e.value = value;
514 return oldValue;
515 }
516 }
517
518 // Add to front of list
519 Entry<K,V> newEntry = new Entry<K,V>(hash, key, value, first);
520 tab[index] = newEntry;
521
522 if ((segcount = ++seg.count) < threshold)
523 return null;
524
525 int bit = (1 << (hash & SEGMENT_MASK));
526 votes = votesForResize;
527 if ((votes & bit) == 0)
528 votes = votesForResize |= bit;
529 }
530 finally {
531 seg.unlock();
532 }
533
534 // Attempt resize if 1/4 segs vote,
535 // or if this seg itself reaches the overall threshold.
536 // (The latter check is just a safeguard to avoid pathological cases.)
537 if (bitcount(votes) >= CONCURRENCY_LEVEL / 4 ||
538 segcount > (threshold * CONCURRENCY_LEVEL))
539 resize(tab);
540
541 return null;
542 }
543
544 public V putIfAbsent(K key, V value) {
545 if (value == null)
546 throw new NullPointerException();
547
548 int hash = hash(key);
549 Segment seg = segments[hash & SEGMENT_MASK];
550 int segcount;
551 Entry<K,V>[] tab;
552 int votes;
553
554 seg.lock();
555 try {
556 tab = table;
557 int index = hash & (tab.length-1);
558 Entry<K,V> first = tab[index];
559
560 for (Entry<K,V> e = first; e != null; e = e.next) {
561 if (e.hash == hash && eq(key, e.key)) {
562 V oldValue = e.value;
563 return oldValue;
564 }
565 }
566
567 // Add to front of list
568 Entry<K,V> newEntry = new Entry<K,V>(hash, key, value, first);
569 tab[index] = newEntry;
570
571 if ((segcount = ++seg.count) < threshold)
572 return null;
573
574 int bit = (1 << (hash & SEGMENT_MASK));
575 votes = votesForResize;
576 if ((votes & bit) == 0)
577 votes = votesForResize |= bit;
578 }
579 finally {
580 seg.unlock();
581 }
582
583 // Attempt resize if 1/4 segs vote,
584 // or if this seg itself reaches the overall threshold.
585 // (The latter check is just a safeguard to avoid pathological cases.)
586 if (bitcount(votes) >= CONCURRENCY_LEVEL / 4 ||
587 segcount > (threshold * CONCURRENCY_LEVEL))
588 resize(tab);
589
590 return value;
591 }
592
593 /**
594 * Gather all locks in order to call rehash, by
595 * recursing within synch blocks for each segment index.
596 * @param index the current segment. initially call value must be 0
597 * @param assumedTab the state of table on first call to resize. If
598 * this changes on any call, the attempt is aborted because the
599 * table has already been resized by another thread.
600 */
601 private void resize(Entry<K,V>[] assumedTab) {
602 boolean ok = true;
603 int lastlocked = 0;
604 for (int i = 0; i < segments.length; ++i) {
605 segments[i].lock();
606 lastlocked = i;
607 if (table != assumedTab) {
608 ok = false;
609 break;
610 }
611 }
612 try {
613 if (ok)
614 rehash();
615 }
616 finally {
617 for (int i = lastlocked; i >= 0; --i)
618 segments[i].unlock();
619 }
620 }
621
622 /**
623 * Rehashes the contents of this map into a new table
624 * with a larger capacity.
625 */
626 private void rehash() {
627 votesForResize = 0; // reset
628
629 Entry<K,V>[] oldTable = table;
630 int oldCapacity = oldTable.length;
631
632 if (oldCapacity >= MAXIMUM_CAPACITY) {
633 threshold = Integer.MAX_VALUE; // avoid retriggering
634 return;
635 }
636
637 int newCapacity = oldCapacity << 1;
638 Entry<K,V>[] newTable = newTable(newCapacity);
639 int mask = newCapacity - 1;
640
641 /*
642 * Reclassify nodes in each list to new Map. Because we are
643 * using power-of-two expansion, the elements from each bin
644 * must either stay at same index, or move to
645 * oldCapacity+index. We also eliminate unnecessary node
646 * creation by catching cases where old nodes can be reused
647 * because their next fields won't change. Statistically, at
648 * the default threshhold, only about one-sixth of them need
649 * cloning. (The nodes they replace will be garbage
650 * collectable as soon as they are no longer referenced by any
651 * reader thread that may be in the midst of traversing table
652 * right now.)
653 */
654
655 for (int i = 0; i < oldCapacity ; i++) {
656 // We need to guarantee that any existing reads of old Map can
657 // proceed. So we cannot yet null out each bin.
658 Entry<K,V> e = oldTable[i];
659
660 if (e != null) {
661 int idx = e.hash & mask;
662 Entry<K,V> next = e.next;
663
664 // Single node on list
665 if (next == null)
666 newTable[idx] = e;
667
668 else {
669 // Reuse trailing consecutive sequence of all same bit
670 Entry<K,V> lastRun = e;
671 int lastIdx = idx;
672 for (Entry<K,V> last = next; last != null; last = last.next) {
673 int k = last.hash & mask;
674 if (k != lastIdx) {
675 lastIdx = k;
676 lastRun = last;
677 }
678 }
679 newTable[lastIdx] = lastRun;
680
681 // Clone all remaining nodes
682 for (Entry<K,V> p = e; p != lastRun; p = p.next) {
683 int k = p.hash & mask;
684 newTable[k] = new Entry<K,V>(p.hash, p.key,
685 p.value, newTable[k]);
686 }
687 }
688 }
689 }
690
691 table = newTable;
692 }
693
694
695 /**
696 * Removes the key (and its corresponding value) from this
697 * table. This method does nothing if the key is not in the table.
698 *
699 * @param key the key that needs to be removed.
700 * @return the value to which the key had been mapped in this table,
701 * or <code>null</code> if the key did not have a mapping.
702 * @exception NullPointerException if the key is
703 * <code>null</code>.
704 */
705 public V remove(Object key) {
706 return remove(key, null);
707 }
708
709
710 /**
711 * Removes the (key, value) pair from this
712 * table. This method does nothing if the key is not in the table,
713 * or if the key is associated with a different value. This method
714 * is needed by EntrySet.
715 *
716 * @param key the key that needs to be removed.
717 * @param value the associated value. If the value is null,
718 * it means "any value".
719 * @return the value to which the key had been mapped in this table,
720 * or <code>null</code> if the key did not have a mapping.
721 * @exception NullPointerException if the key is
722 * <code>null</code>.
723 */
724 private V remove(Object key, V value) {
725 /*
726 Find the entry, then
727 1. Set value field to null, to force get() to retry
728 2. Rebuild the list without this entry.
729 All entries following removed node can stay in list, but
730 all preceeding ones need to be cloned. Traversals rely
731 on this strategy to ensure that elements will not be
732 repeated during iteration.
733 */
734
735 int hash = hash(key);
736 Segment seg = segments[hash & SEGMENT_MASK];
737
738 seg.lock();
739 try {
740 Entry<K,V>[] tab = table;
741 int index = hash & (tab.length-1);
742 Entry<K,V> first = tab[index];
743 Entry<K,V> e = first;
744
745 for (;;) {
746 if (e == null)
747 return null;
748 if (e.hash == hash && eq(key, e.key))
749 break;
750 e = e.next;
751 }
752
753 V oldValue = e.value;
754 if (value != null && !value.equals(oldValue))
755 return null;
756
757 e.value = null;
758
759 Entry<K,V> head = e.next;
760 for (Entry<K,V> p = first; p != e; p = p.next)
761 head = new Entry<K,V>(p.hash, p.key, p.value, head);
762 tab[index] = head;
763 seg.count--;
764 return oldValue;
765 }
766 finally {
767 seg.unlock();
768 }
769 }
770
771
772 /**
773 * Returns <tt>true</tt> if this map maps one or more keys to the
774 * specified value. Note: This method requires a full internal
775 * traversal of the hash table, and so is much slower than
776 * method <tt>containsKey</tt>.
777 *
778 * @param value value whose presence in this map is to be tested.
779 * @return <tt>true</tt> if this map maps one or more keys to the
780 * specified value.
781 * @exception NullPointerException if the value is <code>null</code>.
782 */
783 public boolean containsValue(Object value) {
784
785 if (value == null) throw new NullPointerException();
786
787 for (int s = 0; s < segments.length; ++s) {
788 Segment seg = segments[s];
789 Entry<K,V>[] tab;
790 seg.lock();
791 try {
792 tab = table;
793 }
794 finally {
795 seg.unlock();
796 }
797 for (int i = s; i < tab.length; i+= segments.length) {
798 for (Entry<K,V> e = tab[i]; e != null; e = e.next)
799 if (value.equals(e.value))
800 return true;
801 }
802 }
803 return false;
804 }
805
806 /**
807 * Tests if some key maps into the specified value in this table.
808 * This operation is more expensive than the <code>containsKey</code>
809 * method.<p>
810 *
811 * Note that this method is identical in functionality to containsValue,
812 * (which is part of the Map interface in the collections framework).
813 *
814 * @param value a value to search for.
815 * @return <code>true</code> if and only if some key maps to the
816 * <code>value</code> argument in this table as
817 * determined by the <tt>equals</tt> method;
818 * <code>false</code> otherwise.
819 * @exception NullPointerException if the value is <code>null</code>.
820 * @see #containsKey(Object)
821 * @see #containsValue(Object)
822 * @see Map
823 */
824 public boolean contains(V value) {
825 return containsValue(value);
826 }
827
828 /**
829 * Copies all of the mappings from the specified map to this one.
830 *
831 * These mappings replace any mappings that this map had for any of the
832 * keys currently in the specified Map.
833 *
834 * @param t Mappings to be stored in this map.
835 */
836 public <A extends K, B extends V> void putAll(Map<A, B> t) {
837 int n = t.size();
838 if (n == 0)
839 return;
840
841 // Expand enough to hold at least n elements without resizing.
842 // We can only resize table by factor of two at a time.
843 // It is faster to rehash with fewer elements, so do it now.
844 for(;;) {
845 Entry<K,V>[] tab;
846 int max;
847 // must synch on some segment. pick 0.
848 segments[0].lock();
849 try {
850 tab = table;
851 max = threshold * CONCURRENCY_LEVEL;
852 }
853 finally {
854 segments[0].unlock();
855 }
856 if (n < max)
857 break;
858 resize(tab);
859 }
860
861 for (Iterator<Map.Entry<A,B>> it = t.entrySet().iterator(); it.hasNext();) {
862 Map.Entry<A,B> entry = (Map.Entry<A,B>) it.next();
863 put(entry.getKey(), entry.getValue());
864 }
865 }
866
867 /**
868 * Removes all mappings from this map.
869 */
870 public void clear() {
871 // We don't need all locks at once so long as locks
872 // are obtained in low to high order
873 for (int s = 0; s < segments.length; ++s) {
874 Segment seg = segments[s];
875 seg.lock();
876 try {
877 Entry<K,V>[] tab = table;
878 for (int i = s; i < tab.length; i+= segments.length) {
879 for (Entry<K,V> e = tab[i]; e != null; e = e.next)
880 e.value = null;
881 tab[i] = null;
882 seg.count = 0;
883 }
884 }
885 finally {
886 seg.unlock();
887 }
888 }
889 }
890
891 /**
892 * Returns a shallow copy of this
893 * <tt>ConcurrentHashMap</tt> instance: the keys and
894 * values themselves are not cloned.
895 *
896 * @return a shallow copy of this map.
897 */
898 public Object clone() {
899 // We cannot call super.clone, since it would share final segments array,
900 // and there's no way to reassign finals.
901 return new ConcurrentHashMap<K,V>(this);
902 }
903
904 // Views
905
906 private transient Set<K> keySet = null;
907 private transient Set<Map.Entry<K,V>> entrySet = null;
908 private transient Collection<V> values = null;
909
910 /**
911 * Returns a set view of the keys contained in this map. The set is
912 * backed by the map, so changes to the map are reflected in the set, and
913 * vice-versa. The set supports element removal, which removes the
914 * corresponding mapping from this map, via the <tt>Iterator.remove</tt>,
915 * <tt>Set.remove</tt>, <tt>removeAll</tt>, <tt>retainAll</tt>, and
916 * <tt>clear</tt> operations. It does not support the <tt>add</tt> or
917 * <tt>addAll</tt> operations.
918 *
919 * @return a set view of the keys contained in this map.
920 */
921 public Set<K> keySet() {
922 Set<K> ks = keySet;
923 return (ks != null)? ks : (keySet = new KeySet());
924 }
925
926 private class KeySet extends AbstractSet<K> {
927 public Iterator<K> iterator() {
928 return new KeyIterator();
929 }
930 public int size() {
931 return ConcurrentHashMap.this.size();
932 }
933 public boolean contains(Object o) {
934 return ConcurrentHashMap.this.containsKey(o);
935 }
936 public boolean remove(Object o) {
937 return ConcurrentHashMap.this.remove(o) != null;
938 }
939 public void clear() {
940 ConcurrentHashMap.this.clear();
941 }
942 }
943
944 /**
945 * Returns a collection view of the values contained in this map. The
946 * collection is backed by the map, so changes to the map are reflected in
947 * the collection, and vice-versa. The collection supports element
948 * removal, which removes the corresponding mapping from this map, via the
949 * <tt>Iterator.remove</tt>, <tt>Collection.remove</tt>,
950 * <tt>removeAll</tt>, <tt>retainAll</tt>, and <tt>clear</tt> operations.
951 * It does not support the <tt>add</tt> or <tt>addAll</tt> operations.
952 *
953 * @return a collection view of the values contained in this map.
954 */
955 public Collection<V> values() {
956 Collection<V> vs = values;
957 return (vs != null)? vs : (values = new Values());
958 }
959
960 private class Values extends AbstractCollection<V> {
961 public Iterator<V> iterator() {
962 return new ValueIterator();
963 }
964 public int size() {
965 return ConcurrentHashMap.this.size();
966 }
967 public boolean contains(Object o) {
968 return ConcurrentHashMap.this.containsValue(o);
969 }
970 public void clear() {
971 ConcurrentHashMap.this.clear();
972 }
973 }
974
975 /**
976 * Returns a collection view of the mappings contained in this map. Each
977 * element in the returned collection is a <tt>Map.Entry</tt>. The
978 * collection is backed by the map, so changes to the map are reflected in
979 * the collection, and vice-versa. The collection supports element
980 * removal, which removes the corresponding mapping from the map, via the
981 * <tt>Iterator.remove</tt>, <tt>Collection.remove</tt>,
982 * <tt>removeAll</tt>, <tt>retainAll</tt>, and <tt>clear</tt> operations.
983 * It does not support the <tt>add</tt> or <tt>addAll</tt> operations.
984 *
985 * @return a collection view of the mappings contained in this map.
986 */
987 public Set<Map.Entry<K,V>> entrySet() {
988 Set<Map.Entry<K,V>> es = entrySet;
989 return (es != null) ? es : (entrySet = new EntrySet());
990 }
991
992 private class EntrySet extends AbstractSet<Map.Entry<K,V>> {
993 public Iterator<Map.Entry<K,V>> iterator() {
994 return new EntryIterator();
995 }
996 public boolean contains(Map.Entry<K,V> entry) {
997 V v = ConcurrentHashMap.this.get(entry.getKey());
998 return v != null && v.equals(entry.getValue());
999 }
1000 public boolean remove(Map.Entry<K,V> e) {
1001 return ConcurrentHashMap.this.remove(e.getKey(), e.getValue()) != null;
1002 }
1003 public int size() {
1004 return ConcurrentHashMap.this.size();
1005 }
1006 public void clear() {
1007 ConcurrentHashMap.this.clear();
1008 }
1009 }
1010
1011 /**
1012 * Returns an enumeration of the keys in this table.
1013 *
1014 * @return an enumeration of the keys in this table.
1015 * @see Enumeration
1016 * @see #elements()
1017 * @see #keySet()
1018 * @see Map
1019 */
1020 public Enumeration keys() {
1021 return new KeyIterator();
1022 }
1023
1024 /**
1025 * Returns an enumeration of the values in this table.
1026 * Use the Enumeration methods on the returned object to fetch the elements
1027 * sequentially.
1028 *
1029 * @return an enumeration of the values in this table.
1030 * @see java.util.Enumeration
1031 * @see #keys()
1032 * @see #values()
1033 * @see Map
1034 */
1035 public Enumeration elements() {
1036 return new ValueIterator();
1037 }
1038
1039 /**
1040 * ConcurrentHashMap collision list entry.
1041 */
1042 private static class Entry<K,V> implements Map.Entry<K,V> {
1043 /*
1044 The use of volatile for value field ensures that
1045 we can detect status changes without synchronization.
1046 The other fields are never changed, and are
1047 marked as final.
1048 */
1049
1050 private final K key;
1051 private volatile V value;
1052 private final int hash;
1053 private final Entry<K,V> next;
1054
1055 Entry(int hash, K key, V value, Entry<K,V> next) {
1056 this.value = value;
1057 this.hash = hash;
1058 this.key = key;
1059 this.next = next;
1060 }
1061
1062 // Map.Entry Ops
1063
1064 public K getKey() {
1065 return key;
1066 }
1067
1068 /**
1069 * Get the value. Note: In an entrySet or entrySet.iterator,
1070 * unless you can guarantee lack of concurrent modification,
1071 * <tt>getValue</tt> <em>might</em> return null, reflecting the
1072 * fact that the entry has been concurrently removed. However,
1073 * there are no assurances that concurrent removals will be
1074 * reflected using this method.
1075 *
1076 * @return the current value, or null if the entry has been
1077 * detectably removed.
1078 **/
1079 public V getValue() {
1080 return value;
1081 }
1082
1083 /**
1084 * Set the value of this entry. Note: In an entrySet or
1085 * entrySet.iterator), unless you can guarantee lack of concurrent
1086 * modification, <tt>setValue</tt> is not strictly guaranteed to
1087 * actually replace the value field obtained via the <tt>get</tt>
1088 * operation of the underlying hash table in multithreaded
1089 * applications. If iterator-wide synchronization is not used,
1090 * and any other concurrent <tt>put</tt> or <tt>remove</tt>
1091 * operations occur, sometimes even to <em>other</em> entries,
1092 * then this change is not guaranteed to be reflected in the hash
1093 * table. (It might, or it might not. There are no assurances
1094 * either way.)
1095 *
1096 * @param value the new value.
1097 * @return the previous value, or null if entry has been detectably
1098 * removed.
1099 * @exception NullPointerException if the value is <code>null</code>.
1100 *
1101 **/
1102 public V setValue(V value) {
1103 if (value == null)
1104 throw new NullPointerException();
1105 V oldValue = this.value;
1106 this.value = value;
1107 return oldValue;
1108 }
1109
1110 public boolean equals(Object o) {
1111 if (!(o instanceof Map.Entry))
1112 return false;
1113 Map.Entry e = (Map.Entry)o;
1114 return (key.equals(e.getKey()) && value.equals(e.getValue()));
1115 }
1116
1117 public int hashCode() {
1118 return key.hashCode() ^ value.hashCode();
1119 }
1120
1121 public String toString() {
1122 return key + "=" + value;
1123 }
1124
1125 }
1126
1127 private abstract class HashIterator<T> implements Iterator<T>, Enumeration {
1128 private final Entry<K,V>[] tab; // snapshot of table
1129 private int index; // current slot
1130 Entry<K,V> entry = null; // current node of slot
1131 K currentKey; // key for current node
1132 V currentValue; // value for current node
1133 private Entry lastReturned = null; // last node returned by next
1134
1135 private HashIterator() {
1136 // force all segments to synch
1137 for (int i = 0; i < segments.length; ++i) {
1138 segments[i].lock();
1139 segments[i].unlock();
1140 }
1141 tab = table;
1142 index = tab.length - 1;
1143 }
1144
1145 public boolean hasMoreElements() { return hasNext(); }
1146 public Object nextElement() { return next(); }
1147
1148 public boolean hasNext() {
1149 /*
1150 currentkey and currentValue are set here to ensure that next()
1151 returns normally if hasNext() returns true. This avoids
1152 surprises especially when final element is removed during
1153 traversal -- instead, we just ignore the removal during
1154 current traversal.
1155 */
1156
1157 while (true) {
1158 if (entry != null) {
1159 V v = entry.value;
1160 if (v != null) {
1161 currentKey = entry.key;
1162 currentValue = v;
1163 return true;
1164 }
1165 else
1166 entry = entry.next;
1167 }
1168
1169 while (entry == null && index >= 0)
1170 entry = tab[index--];
1171
1172 if (entry == null) {
1173 currentKey = null;
1174 currentValue = null;
1175 return false;
1176 }
1177 }
1178 }
1179
1180 abstract T returnValueOfNext();
1181
1182 public T next() {
1183 if (currentKey == null && !hasNext())
1184 throw new NoSuchElementException();
1185
1186 T result = returnValueOfNext();
1187 lastReturned = entry;
1188 currentKey = null;
1189 currentValue = null;
1190 entry = entry.next;
1191 return result;
1192 }
1193
1194 public void remove() {
1195 if (lastReturned == null)
1196 throw new IllegalStateException();
1197 ConcurrentHashMap.this.remove(lastReturned.key);
1198 lastReturned = null;
1199 }
1200
1201 }
1202
1203 private class KeyIterator extends HashIterator<K> {
1204 K returnValueOfNext() { return currentKey; }
1205 public K next() { return super.next(); }
1206 }
1207
1208 private class ValueIterator extends HashIterator<V> {
1209 V returnValueOfNext() { return currentValue; }
1210 public V next() { return super.next(); }
1211 }
1212
1213 private class EntryIterator extends HashIterator<Map.Entry<K,V>> {
1214 Map.Entry<K,V> returnValueOfNext() { return entry; }
1215 public Map.Entry<K,V> next() { return super.next(); }
1216 }
1217
1218 /**
1219 * Save the state of the <tt>ConcurrentHashMap</tt>
1220 * instance to a stream (i.e.,
1221 * serialize it).
1222 *
1223 * @serialData
1224 * An estimate of the table size, followed by
1225 * the key (Object) and value (Object)
1226 * for each key-value mapping, followed by a null pair.
1227 * The key-value mappings are emitted in no particular order.
1228 */
1229 private void writeObject(java.io.ObjectOutputStream s) throws IOException {
1230 // Write out the loadfactor, and any hidden stuff
1231 s.defaultWriteObject();
1232
1233 // Write out capacity estimate. It is OK if this
1234 // changes during the write, since it is only used by
1235 // readObject to set initial capacity, to avoid needless resizings.
1236
1237 int cap;
1238 segments[0].lock();
1239 try {
1240 cap = table.length;
1241 }
1242 finally {
1243 segments[0].unlock();
1244 }
1245 s.writeInt(cap);
1246
1247 // Write out keys and values (alternating)
1248 for (int k = 0; k < segments.length; ++k) {
1249 Segment seg = segments[k];
1250 Entry[] tab;
1251 seg.lock();
1252 try {
1253 tab = table;
1254 }
1255 finally {
1256 seg.unlock();
1257 }
1258 for (int i = k; i < tab.length; i+= segments.length) {
1259 for (Entry e = tab[i]; e != null; e = e.next) {
1260 s.writeObject(e.key);
1261 s.writeObject(e.value);
1262 }
1263 }
1264 }
1265
1266 s.writeObject(null);
1267 s.writeObject(null);
1268 }
1269
1270 /**
1271 * Reconstitute the <tt>ConcurrentHashMap</tt>
1272 * instance from a stream (i.e.,
1273 * deserialize it).
1274 */
1275 private void readObject(java.io.ObjectInputStream s)
1276 throws IOException, ClassNotFoundException {
1277
1278 // Read in the threshold, loadfactor, and any hidden stuff
1279 s.defaultReadObject();
1280
1281 int cap = s.readInt();
1282 table = newTable(cap);
1283 for (int i = 0; i < segments.length; ++i)
1284 segments[i] = new Segment();
1285
1286
1287 // Read the keys and values, and put the mappings in the table
1288 while (true) {
1289 K key = (K) s.readObject();
1290 V value = (V) s.readObject();
1291 if (key == null)
1292 break;
1293 put(key, value);
1294 }
1295 }
1296 }