ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/jsr166/jsr166/src/main/java/util/Map.java
Revision: 1.1
Committed: Mon Dec 14 20:03:55 2015 UTC (8 years, 5 months ago) by jsr166
Branch: MAIN
Log Message:
import upstream Map.java for "concurrent" bugfixing

File Contents

# Content
1 /*
2 * Copyright (c) 1997, 2013, Oracle and/or its affiliates. All rights reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation. Oracle designates this
8 * particular file as subject to the "Classpath" exception as provided
9 * by Oracle in the LICENSE file that accompanied this code.
10 *
11 * This code is distributed in the hope that it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14 * version 2 for more details (a copy is included in the LICENSE file that
15 * accompanied this code).
16 *
17 * You should have received a copy of the GNU General Public License version
18 * 2 along with this work; if not, write to the Free Software Foundation,
19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
20 *
21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
22 * or visit www.oracle.com if you need additional information or have any
23 * questions.
24 */
25
26 package java.util;
27
28 import java.util.function.BiConsumer;
29 import java.util.function.BiFunction;
30 import java.util.function.Function;
31 import java.io.Serializable;
32
33 /**
34 * An object that maps keys to values. A map cannot contain duplicate keys;
35 * each key can map to at most one value.
36 *
37 * <p>This interface takes the place of the {@code Dictionary} class, which
38 * was a totally abstract class rather than an interface.
39 *
40 * <p>The {@code Map} interface provides three <i>collection views</i>, which
41 * allow a map's contents to be viewed as a set of keys, collection of values,
42 * or set of key-value mappings. The <i>order</i> of a map is defined as
43 * the order in which the iterators on the map's collection views return their
44 * elements. Some map implementations, like the {@code TreeMap} class, make
45 * specific guarantees as to their order; others, like the {@code HashMap}
46 * class, do not.
47 *
48 * <p>Note: great care must be exercised if mutable objects are used as map
49 * keys. The behavior of a map is not specified if the value of an object is
50 * changed in a manner that affects {@code equals} comparisons while the
51 * object is a key in the map. A special case of this prohibition is that it
52 * is not permissible for a map to contain itself as a key. While it is
53 * permissible for a map to contain itself as a value, extreme caution is
54 * advised: the {@code equals} and {@code hashCode} methods are no longer
55 * well defined on such a map.
56 *
57 * <p>All general-purpose map implementation classes should provide two
58 * "standard" constructors: a void (no arguments) constructor which creates an
59 * empty map, and a constructor with a single argument of type {@code Map},
60 * which creates a new map with the same key-value mappings as its argument.
61 * In effect, the latter constructor allows the user to copy any map,
62 * producing an equivalent map of the desired class. There is no way to
63 * enforce this recommendation (as interfaces cannot contain constructors) but
64 * all of the general-purpose map implementations in the JDK comply.
65 *
66 * <p>The "destructive" methods contained in this interface, that is, the
67 * methods that modify the map on which they operate, are specified to throw
68 * {@code UnsupportedOperationException} if this map does not support the
69 * operation. If this is the case, these methods may, but are not required
70 * to, throw an {@code UnsupportedOperationException} if the invocation would
71 * have no effect on the map. For example, invoking the {@link #putAll(Map)}
72 * method on an unmodifiable map may, but is not required to, throw the
73 * exception if the map whose mappings are to be "superimposed" is empty.
74 *
75 * <p>Some map implementations have restrictions on the keys and values they
76 * may contain. For example, some implementations prohibit null keys and
77 * values, and some have restrictions on the types of their keys. Attempting
78 * to insert an ineligible key or value throws an unchecked exception,
79 * typically {@code NullPointerException} or {@code ClassCastException}.
80 * Attempting to query the presence of an ineligible key or value may throw an
81 * exception, or it may simply return false; some implementations will exhibit
82 * the former behavior and some will exhibit the latter. More generally,
83 * attempting an operation on an ineligible key or value whose completion
84 * would not result in the insertion of an ineligible element into the map may
85 * throw an exception or it may succeed, at the option of the implementation.
86 * Such exceptions are marked as "optional" in the specification for this
87 * interface.
88 *
89 * <p>Many methods in Collections Framework interfaces are defined
90 * in terms of the {@link Object#equals(Object) equals} method. For
91 * example, the specification for the {@link #containsKey(Object)
92 * containsKey(Object key)} method says: "returns {@code true} if and
93 * only if this map contains a mapping for a key {@code k} such that
94 * {@code (key==null ? k==null : key.equals(k))}." This specification should
95 * <i>not</i> be construed to imply that invoking {@code Map.containsKey}
96 * with a non-null argument {@code key} will cause {@code key.equals(k)} to
97 * be invoked for any key {@code k}. Implementations are free to
98 * implement optimizations whereby the {@code equals} invocation is avoided,
99 * for example, by first comparing the hash codes of the two keys. (The
100 * {@link Object#hashCode()} specification guarantees that two objects with
101 * unequal hash codes cannot be equal.) More generally, implementations of
102 * the various Collections Framework interfaces are free to take advantage of
103 * the specified behavior of underlying {@link Object} methods wherever the
104 * implementor deems it appropriate.
105 *
106 * <p>Some map operations which perform recursive traversal of the map may fail
107 * with an exception for self-referential instances where the map directly or
108 * indirectly contains itself. This includes the {@code clone()},
109 * {@code equals()}, {@code hashCode()} and {@code toString()} methods.
110 * Implementations may optionally handle the self-referential scenario, however
111 * most current implementations do not do so.
112 *
113 * <p>This interface is a member of the
114 * <a href="{@docRoot}/../technotes/guides/collections/index.html">
115 * Java Collections Framework</a>.
116 *
117 * @param <K> the type of keys maintained by this map
118 * @param <V> the type of mapped values
119 *
120 * @author Josh Bloch
121 * @see HashMap
122 * @see TreeMap
123 * @see Hashtable
124 * @see SortedMap
125 * @see Collection
126 * @see Set
127 * @since 1.2
128 */
129 public interface Map<K,V> {
130 // Query Operations
131
132 /**
133 * Returns the number of key-value mappings in this map. If the
134 * map contains more than {@code Integer.MAX_VALUE} elements, returns
135 * {@code Integer.MAX_VALUE}.
136 *
137 * @return the number of key-value mappings in this map
138 */
139 int size();
140
141 /**
142 * Returns {@code true} if this map contains no key-value mappings.
143 *
144 * @return {@code true} if this map contains no key-value mappings
145 */
146 boolean isEmpty();
147
148 /**
149 * Returns {@code true} if this map contains a mapping for the specified
150 * key. More formally, returns {@code true} if and only if
151 * this map contains a mapping for a key {@code k} such that
152 * {@code Objects.equals(key, k)}. (There can be
153 * at most one such mapping.)
154 *
155 * @param key key whose presence in this map is to be tested
156 * @return {@code true} if this map contains a mapping for the specified
157 * key
158 * @throws ClassCastException if the key is of an inappropriate type for
159 * this map
160 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
161 * @throws NullPointerException if the specified key is null and this map
162 * does not permit null keys
163 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
164 */
165 boolean containsKey(Object key);
166
167 /**
168 * Returns {@code true} if this map maps one or more keys to the
169 * specified value. More formally, returns {@code true} if and only if
170 * this map contains at least one mapping to a value {@code v} such that
171 * {@code Objects.equals(value, v)}. This operation
172 * will probably require time linear in the map size for most
173 * implementations of the {@code Map} interface.
174 *
175 * @param value value whose presence in this map is to be tested
176 * @return {@code true} if this map maps one or more keys to the
177 * specified value
178 * @throws ClassCastException if the value is of an inappropriate type for
179 * this map
180 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
181 * @throws NullPointerException if the specified value is null and this
182 * map does not permit null values
183 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
184 */
185 boolean containsValue(Object value);
186
187 /**
188 * Returns the value to which the specified key is mapped,
189 * or {@code null} if this map contains no mapping for the key.
190 *
191 * <p>More formally, if this map contains a mapping from a key
192 * {@code k} to a value {@code v} such that
193 * {@code Objects.equals(key, k)},
194 * then this method returns {@code v}; otherwise
195 * it returns {@code null}. (There can be at most one such mapping.)
196 *
197 * <p>If this map permits null values, then a return value of
198 * {@code null} does not <i>necessarily</i> indicate that the map
199 * contains no mapping for the key; it's also possible that the map
200 * explicitly maps the key to {@code null}. The {@link #containsKey
201 * containsKey} operation may be used to distinguish these two cases.
202 *
203 * @param key the key whose associated value is to be returned
204 * @return the value to which the specified key is mapped, or
205 * {@code null} if this map contains no mapping for the key
206 * @throws ClassCastException if the key is of an inappropriate type for
207 * this map
208 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
209 * @throws NullPointerException if the specified key is null and this map
210 * does not permit null keys
211 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
212 */
213 V get(Object key);
214
215 // Modification Operations
216
217 /**
218 * Associates the specified value with the specified key in this map
219 * (optional operation). If the map previously contained a mapping for
220 * the key, the old value is replaced by the specified value. (A map
221 * {@code m} is said to contain a mapping for a key {@code k} if and only
222 * if {@link #containsKey(Object) m.containsKey(k)} would return
223 * {@code true}.)
224 *
225 * @param key key with which the specified value is to be associated
226 * @param value value to be associated with the specified key
227 * @return the previous value associated with {@code key}, or
228 * {@code null} if there was no mapping for {@code key}.
229 * (A {@code null} return can also indicate that the map
230 * previously associated {@code null} with {@code key},
231 * if the implementation supports {@code null} values.)
232 * @throws UnsupportedOperationException if the {@code put} operation
233 * is not supported by this map
234 * @throws ClassCastException if the class of the specified key or value
235 * prevents it from being stored in this map
236 * @throws NullPointerException if the specified key or value is null
237 * and this map does not permit null keys or values
238 * @throws IllegalArgumentException if some property of the specified key
239 * or value prevents it from being stored in this map
240 */
241 V put(K key, V value);
242
243 /**
244 * Removes the mapping for a key from this map if it is present
245 * (optional operation). More formally, if this map contains a mapping
246 * from key {@code k} to value {@code v} such that
247 * {@code Objects.equals(key, k)}, that mapping
248 * is removed. (The map can contain at most one such mapping.)
249 *
250 * <p>Returns the value to which this map previously associated the key,
251 * or {@code null} if the map contained no mapping for the key.
252 *
253 * <p>If this map permits null values, then a return value of
254 * {@code null} does not <i>necessarily</i> indicate that the map
255 * contained no mapping for the key; it's also possible that the map
256 * explicitly mapped the key to {@code null}.
257 *
258 * <p>The map will not contain a mapping for the specified key once the
259 * call returns.
260 *
261 * @param key key whose mapping is to be removed from the map
262 * @return the previous value associated with {@code key}, or
263 * {@code null} if there was no mapping for {@code key}.
264 * @throws UnsupportedOperationException if the {@code remove} operation
265 * is not supported by this map
266 * @throws ClassCastException if the key is of an inappropriate type for
267 * this map
268 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
269 * @throws NullPointerException if the specified key is null and this
270 * map does not permit null keys
271 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
272 */
273 V remove(Object key);
274
275
276 // Bulk Operations
277
278 /**
279 * Copies all of the mappings from the specified map to this map
280 * (optional operation). The effect of this call is equivalent to that
281 * of calling {@link #put(Object,Object) put(k, v)} on this map once
282 * for each mapping from key {@code k} to value {@code v} in the
283 * specified map. The behavior of this operation is undefined if the
284 * specified map is modified while the operation is in progress.
285 *
286 * @param m mappings to be stored in this map
287 * @throws UnsupportedOperationException if the {@code putAll} operation
288 * is not supported by this map
289 * @throws ClassCastException if the class of a key or value in the
290 * specified map prevents it from being stored in this map
291 * @throws NullPointerException if the specified map is null, or if
292 * this map does not permit null keys or values, and the
293 * specified map contains null keys or values
294 * @throws IllegalArgumentException if some property of a key or value in
295 * the specified map prevents it from being stored in this map
296 */
297 void putAll(Map<? extends K, ? extends V> m);
298
299 /**
300 * Removes all of the mappings from this map (optional operation).
301 * The map will be empty after this call returns.
302 *
303 * @throws UnsupportedOperationException if the {@code clear} operation
304 * is not supported by this map
305 */
306 void clear();
307
308
309 // Views
310
311 /**
312 * Returns a {@link Set} view of the keys contained in this map.
313 * The set is backed by the map, so changes to the map are
314 * reflected in the set, and vice-versa. If the map is modified
315 * while an iteration over the set is in progress (except through
316 * the iterator's own {@code remove} operation), the results of
317 * the iteration are undefined. The set supports element removal,
318 * which removes the corresponding mapping from the map, via the
319 * {@code Iterator.remove}, {@code Set.remove},
320 * {@code removeAll}, {@code retainAll}, and {@code clear}
321 * operations. It does not support the {@code add} or {@code addAll}
322 * operations.
323 *
324 * @return a set view of the keys contained in this map
325 */
326 Set<K> keySet();
327
328 /**
329 * Returns a {@link Collection} view of the values contained in this map.
330 * The collection is backed by the map, so changes to the map are
331 * reflected in the collection, and vice-versa. If the map is
332 * modified while an iteration over the collection is in progress
333 * (except through the iterator's own {@code remove} operation),
334 * the results of the iteration are undefined. The collection
335 * supports element removal, which removes the corresponding
336 * mapping from the map, via the {@code Iterator.remove},
337 * {@code Collection.remove}, {@code removeAll},
338 * {@code retainAll} and {@code clear} operations. It does not
339 * support the {@code add} or {@code addAll} operations.
340 *
341 * @return a collection view of the values contained in this map
342 */
343 Collection<V> values();
344
345 /**
346 * Returns a {@link Set} view of the mappings contained in this map.
347 * The set is backed by the map, so changes to the map are
348 * reflected in the set, and vice-versa. If the map is modified
349 * while an iteration over the set is in progress (except through
350 * the iterator's own {@code remove} operation, or through the
351 * {@code setValue} operation on a map entry returned by the
352 * iterator) the results of the iteration are undefined. The set
353 * supports element removal, which removes the corresponding
354 * mapping from the map, via the {@code Iterator.remove},
355 * {@code Set.remove}, {@code removeAll}, {@code retainAll} and
356 * {@code clear} operations. It does not support the
357 * {@code add} or {@code addAll} operations.
358 *
359 * @return a set view of the mappings contained in this map
360 */
361 Set<Map.Entry<K, V>> entrySet();
362
363 /**
364 * A map entry (key-value pair). The {@code Map.entrySet} method returns
365 * a collection-view of the map, whose elements are of this class. The
366 * <i>only</i> way to obtain a reference to a map entry is from the
367 * iterator of this collection-view. These {@code Map.Entry} objects are
368 * valid <i>only</i> for the duration of the iteration; more formally,
369 * the behavior of a map entry is undefined if the backing map has been
370 * modified after the entry was returned by the iterator, except through
371 * the {@code setValue} operation on the map entry.
372 *
373 * @see Map#entrySet()
374 * @since 1.2
375 */
376 interface Entry<K,V> {
377 /**
378 * Returns the key corresponding to this entry.
379 *
380 * @return the key corresponding to this entry
381 * @throws IllegalStateException implementations may, but are not
382 * required to, throw this exception if the entry has been
383 * removed from the backing map.
384 */
385 K getKey();
386
387 /**
388 * Returns the value corresponding to this entry. If the mapping
389 * has been removed from the backing map (by the iterator's
390 * {@code remove} operation), the results of this call are undefined.
391 *
392 * @return the value corresponding to this entry
393 * @throws IllegalStateException implementations may, but are not
394 * required to, throw this exception if the entry has been
395 * removed from the backing map.
396 */
397 V getValue();
398
399 /**
400 * Replaces the value corresponding to this entry with the specified
401 * value (optional operation). (Writes through to the map.) The
402 * behavior of this call is undefined if the mapping has already been
403 * removed from the map (by the iterator's {@code remove} operation).
404 *
405 * @param value new value to be stored in this entry
406 * @return old value corresponding to the entry
407 * @throws UnsupportedOperationException if the {@code put} operation
408 * is not supported by the backing map
409 * @throws ClassCastException if the class of the specified value
410 * prevents it from being stored in the backing map
411 * @throws NullPointerException if the backing map does not permit
412 * null values, and the specified value is null
413 * @throws IllegalArgumentException if some property of this value
414 * prevents it from being stored in the backing map
415 * @throws IllegalStateException implementations may, but are not
416 * required to, throw this exception if the entry has been
417 * removed from the backing map.
418 */
419 V setValue(V value);
420
421 /**
422 * Compares the specified object with this entry for equality.
423 * Returns {@code true} if the given object is also a map entry and
424 * the two entries represent the same mapping. More formally, two
425 * entries {@code e1} and {@code e2} represent the same mapping
426 * if<pre>
427 * (e1.getKey()==null ?
428 * e2.getKey()==null : e1.getKey().equals(e2.getKey())) &amp;&amp;
429 * (e1.getValue()==null ?
430 * e2.getValue()==null : e1.getValue().equals(e2.getValue()))
431 * </pre>
432 * This ensures that the {@code equals} method works properly across
433 * different implementations of the {@code Map.Entry} interface.
434 *
435 * @param o object to be compared for equality with this map entry
436 * @return {@code true} if the specified object is equal to this map
437 * entry
438 */
439 boolean equals(Object o);
440
441 /**
442 * Returns the hash code value for this map entry. The hash code
443 * of a map entry {@code e} is defined to be: <pre>
444 * (e.getKey()==null ? 0 : e.getKey().hashCode()) ^
445 * (e.getValue()==null ? 0 : e.getValue().hashCode())
446 * </pre>
447 * This ensures that {@code e1.equals(e2)} implies that
448 * {@code e1.hashCode()==e2.hashCode()} for any two Entries
449 * {@code e1} and {@code e2}, as required by the general
450 * contract of {@code Object.hashCode}.
451 *
452 * @return the hash code value for this map entry
453 * @see Object#hashCode()
454 * @see Object#equals(Object)
455 * @see #equals(Object)
456 */
457 int hashCode();
458
459 /**
460 * Returns a comparator that compares {@link Map.Entry} in natural order on key.
461 *
462 * <p>The returned comparator is serializable and throws {@link
463 * NullPointerException} when comparing an entry with a null key.
464 *
465 * @param <K> the {@link Comparable} type of then map keys
466 * @param <V> the type of the map values
467 * @return a comparator that compares {@link Map.Entry} in natural order on key.
468 * @see Comparable
469 * @since 1.8
470 */
471 public static <K extends Comparable<? super K>, V> Comparator<Map.Entry<K,V>> comparingByKey() {
472 return (Comparator<Map.Entry<K, V>> & Serializable)
473 (c1, c2) -> c1.getKey().compareTo(c2.getKey());
474 }
475
476 /**
477 * Returns a comparator that compares {@link Map.Entry} in natural order on value.
478 *
479 * <p>The returned comparator is serializable and throws {@link
480 * NullPointerException} when comparing an entry with null values.
481 *
482 * @param <K> the type of the map keys
483 * @param <V> the {@link Comparable} type of the map values
484 * @return a comparator that compares {@link Map.Entry} in natural order on value.
485 * @see Comparable
486 * @since 1.8
487 */
488 public static <K, V extends Comparable<? super V>> Comparator<Map.Entry<K,V>> comparingByValue() {
489 return (Comparator<Map.Entry<K, V>> & Serializable)
490 (c1, c2) -> c1.getValue().compareTo(c2.getValue());
491 }
492
493 /**
494 * Returns a comparator that compares {@link Map.Entry} by key using the given
495 * {@link Comparator}.
496 *
497 * <p>The returned comparator is serializable if the specified comparator
498 * is also serializable.
499 *
500 * @param <K> the type of the map keys
501 * @param <V> the type of the map values
502 * @param cmp the key {@link Comparator}
503 * @return a comparator that compares {@link Map.Entry} by the key.
504 * @since 1.8
505 */
506 public static <K, V> Comparator<Map.Entry<K, V>> comparingByKey(Comparator<? super K> cmp) {
507 Objects.requireNonNull(cmp);
508 return (Comparator<Map.Entry<K, V>> & Serializable)
509 (c1, c2) -> cmp.compare(c1.getKey(), c2.getKey());
510 }
511
512 /**
513 * Returns a comparator that compares {@link Map.Entry} by value using the given
514 * {@link Comparator}.
515 *
516 * <p>The returned comparator is serializable if the specified comparator
517 * is also serializable.
518 *
519 * @param <K> the type of the map keys
520 * @param <V> the type of the map values
521 * @param cmp the value {@link Comparator}
522 * @return a comparator that compares {@link Map.Entry} by the value.
523 * @since 1.8
524 */
525 public static <K, V> Comparator<Map.Entry<K, V>> comparingByValue(Comparator<? super V> cmp) {
526 Objects.requireNonNull(cmp);
527 return (Comparator<Map.Entry<K, V>> & Serializable)
528 (c1, c2) -> cmp.compare(c1.getValue(), c2.getValue());
529 }
530 }
531
532 // Comparison and hashing
533
534 /**
535 * Compares the specified object with this map for equality. Returns
536 * {@code true} if the given object is also a map and the two maps
537 * represent the same mappings. More formally, two maps {@code m1} and
538 * {@code m2} represent the same mappings if
539 * {@code m1.entrySet().equals(m2.entrySet())}. This ensures that the
540 * {@code equals} method works properly across different implementations
541 * of the {@code Map} interface.
542 *
543 * @param o object to be compared for equality with this map
544 * @return {@code true} if the specified object is equal to this map
545 */
546 boolean equals(Object o);
547
548 /**
549 * Returns the hash code value for this map. The hash code of a map is
550 * defined to be the sum of the hash codes of each entry in the map's
551 * {@code entrySet()} view. This ensures that {@code m1.equals(m2)}
552 * implies that {@code m1.hashCode()==m2.hashCode()} for any two maps
553 * {@code m1} and {@code m2}, as required by the general contract of
554 * {@link Object#hashCode}.
555 *
556 * @return the hash code value for this map
557 * @see Map.Entry#hashCode()
558 * @see Object#equals(Object)
559 * @see #equals(Object)
560 */
561 int hashCode();
562
563 // Defaultable methods
564
565 /**
566 * Returns the value to which the specified key is mapped, or
567 * {@code defaultValue} if this map contains no mapping for the key.
568 *
569 * @implSpec
570 * The default implementation makes no guarantees about synchronization
571 * or atomicity properties of this method. Any implementation providing
572 * atomicity guarantees must override this method and document its
573 * concurrency properties.
574 *
575 * @param key the key whose associated value is to be returned
576 * @param defaultValue the default mapping of the key
577 * @return the value to which the specified key is mapped, or
578 * {@code defaultValue} if this map contains no mapping for the key
579 * @throws ClassCastException if the key is of an inappropriate type for
580 * this map
581 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
582 * @throws NullPointerException if the specified key is null and this map
583 * does not permit null keys
584 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
585 * @since 1.8
586 */
587 default V getOrDefault(Object key, V defaultValue) {
588 V v;
589 return (((v = get(key)) != null) || containsKey(key))
590 ? v
591 : defaultValue;
592 }
593
594 /**
595 * Performs the given action for each entry in this map until all entries
596 * have been processed or the action throws an exception. Unless
597 * otherwise specified by the implementing class, actions are performed in
598 * the order of entry set iteration (if an iteration order is specified.)
599 * Exceptions thrown by the action are relayed to the caller.
600 *
601 * @implSpec
602 * The default implementation is equivalent to, for this {@code map}:
603 * <pre> {@code
604 * for (Map.Entry<K, V> entry : map.entrySet())
605 * action.accept(entry.getKey(), entry.getValue());
606 * }</pre>
607 *
608 * The default implementation makes no guarantees about synchronization
609 * or atomicity properties of this method. Any implementation providing
610 * atomicity guarantees must override this method and document its
611 * concurrency properties.
612 *
613 * @param action The action to be performed for each entry
614 * @throws NullPointerException if the specified action is null
615 * @throws ConcurrentModificationException if an entry is found to be
616 * removed during iteration
617 * @since 1.8
618 */
619 default void forEach(BiConsumer<? super K, ? super V> action) {
620 Objects.requireNonNull(action);
621 for (Map.Entry<K, V> entry : entrySet()) {
622 K k;
623 V v;
624 try {
625 k = entry.getKey();
626 v = entry.getValue();
627 } catch (IllegalStateException ise) {
628 // this usually means the entry is no longer in the map.
629 throw new ConcurrentModificationException(ise);
630 }
631 action.accept(k, v);
632 }
633 }
634
635 /**
636 * Replaces each entry's value with the result of invoking the given
637 * function on that entry until all entries have been processed or the
638 * function throws an exception. Exceptions thrown by the function are
639 * relayed to the caller.
640 *
641 * @implSpec
642 * <p>The default implementation is equivalent to, for this {@code map}:
643 * <pre> {@code
644 * for (Map.Entry<K, V> entry : map.entrySet())
645 * entry.setValue(function.apply(entry.getKey(), entry.getValue()));
646 * }</pre>
647 *
648 * <p>The default implementation makes no guarantees about synchronization
649 * or atomicity properties of this method. Any implementation providing
650 * atomicity guarantees must override this method and document its
651 * concurrency properties.
652 *
653 * @param function the function to apply to each entry
654 * @throws UnsupportedOperationException if the {@code set} operation
655 * is not supported by this map's entry set iterator.
656 * @throws ClassCastException if the class of a replacement value
657 * prevents it from being stored in this map
658 * @throws NullPointerException if the specified function is null, or the
659 * specified replacement value is null, and this map does not permit null
660 * values
661 * @throws ClassCastException if a replacement value is of an inappropriate
662 * type for this map
663 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
664 * @throws NullPointerException if function or a replacement value is null,
665 * and this map does not permit null keys or values
666 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
667 * @throws IllegalArgumentException if some property of a replacement value
668 * prevents it from being stored in this map
669 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
670 * @throws ConcurrentModificationException if an entry is found to be
671 * removed during iteration
672 * @since 1.8
673 */
674 default void replaceAll(BiFunction<? super K, ? super V, ? extends V> function) {
675 Objects.requireNonNull(function);
676 for (Map.Entry<K, V> entry : entrySet()) {
677 K k;
678 V v;
679 try {
680 k = entry.getKey();
681 v = entry.getValue();
682 } catch (IllegalStateException ise) {
683 // this usually means the entry is no longer in the map.
684 throw new ConcurrentModificationException(ise);
685 }
686
687 // ise thrown from function is not a cme.
688 v = function.apply(k, v);
689
690 try {
691 entry.setValue(v);
692 } catch (IllegalStateException ise) {
693 // this usually means the entry is no longer in the map.
694 throw new ConcurrentModificationException(ise);
695 }
696 }
697 }
698
699 /**
700 * If the specified key is not already associated with a value (or is mapped
701 * to {@code null}) associates it with the given value and returns
702 * {@code null}, else returns the current value.
703 *
704 * @implSpec
705 * The default implementation is equivalent to, for this {@code
706 * map}:
707 *
708 * <pre> {@code
709 * V v = map.get(key);
710 * if (v == null)
711 * v = map.put(key, value);
712 *
713 * return v;
714 * }</pre>
715 *
716 * <p>The default implementation makes no guarantees about synchronization
717 * or atomicity properties of this method. Any implementation providing
718 * atomicity guarantees must override this method and document its
719 * concurrency properties.
720 *
721 * @param key key with which the specified value is to be associated
722 * @param value value to be associated with the specified key
723 * @return the previous value associated with the specified key, or
724 * {@code null} if there was no mapping for the key.
725 * (A {@code null} return can also indicate that the map
726 * previously associated {@code null} with the key,
727 * if the implementation supports null values.)
728 * @throws UnsupportedOperationException if the {@code put} operation
729 * is not supported by this map
730 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
731 * @throws ClassCastException if the key or value is of an inappropriate
732 * type for this map
733 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
734 * @throws NullPointerException if the specified key or value is null,
735 * and this map does not permit null keys or values
736 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
737 * @throws IllegalArgumentException if some property of the specified key
738 * or value prevents it from being stored in this map
739 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
740 * @since 1.8
741 */
742 default V putIfAbsent(K key, V value) {
743 V v = get(key);
744 if (v == null) {
745 v = put(key, value);
746 }
747
748 return v;
749 }
750
751 /**
752 * Removes the entry for the specified key only if it is currently
753 * mapped to the specified value.
754 *
755 * @implSpec
756 * The default implementation is equivalent to, for this {@code map}:
757 *
758 * <pre> {@code
759 * if (map.containsKey(key) && Objects.equals(map.get(key), value)) {
760 * map.remove(key);
761 * return true;
762 * } else
763 * return false;
764 * }</pre>
765 *
766 * <p>The default implementation makes no guarantees about synchronization
767 * or atomicity properties of this method. Any implementation providing
768 * atomicity guarantees must override this method and document its
769 * concurrency properties.
770 *
771 * @param key key with which the specified value is associated
772 * @param value value expected to be associated with the specified key
773 * @return {@code true} if the value was removed
774 * @throws UnsupportedOperationException if the {@code remove} operation
775 * is not supported by this map
776 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
777 * @throws ClassCastException if the key or value is of an inappropriate
778 * type for this map
779 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
780 * @throws NullPointerException if the specified key or value is null,
781 * and this map does not permit null keys or values
782 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
783 * @since 1.8
784 */
785 default boolean remove(Object key, Object value) {
786 Object curValue = get(key);
787 if (!Objects.equals(curValue, value) ||
788 (curValue == null && !containsKey(key))) {
789 return false;
790 }
791 remove(key);
792 return true;
793 }
794
795 /**
796 * Replaces the entry for the specified key only if currently
797 * mapped to the specified value.
798 *
799 * @implSpec
800 * The default implementation is equivalent to, for this {@code map}:
801 *
802 * <pre> {@code
803 * if (map.containsKey(key) && Objects.equals(map.get(key), value)) {
804 * map.put(key, newValue);
805 * return true;
806 * } else
807 * return false;
808 * }</pre>
809 *
810 * The default implementation does not throw NullPointerException
811 * for maps that do not support null values if oldValue is null unless
812 * newValue is also null.
813 *
814 * <p>The default implementation makes no guarantees about synchronization
815 * or atomicity properties of this method. Any implementation providing
816 * atomicity guarantees must override this method and document its
817 * concurrency properties.
818 *
819 * @param key key with which the specified value is associated
820 * @param oldValue value expected to be associated with the specified key
821 * @param newValue value to be associated with the specified key
822 * @return {@code true} if the value was replaced
823 * @throws UnsupportedOperationException if the {@code put} operation
824 * is not supported by this map
825 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
826 * @throws ClassCastException if the class of a specified key or value
827 * prevents it from being stored in this map
828 * @throws NullPointerException if a specified key or newValue is null,
829 * and this map does not permit null keys or values
830 * @throws NullPointerException if oldValue is null and this map does not
831 * permit null values
832 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
833 * @throws IllegalArgumentException if some property of a specified key
834 * or value prevents it from being stored in this map
835 * @since 1.8
836 */
837 default boolean replace(K key, V oldValue, V newValue) {
838 Object curValue = get(key);
839 if (!Objects.equals(curValue, oldValue) ||
840 (curValue == null && !containsKey(key))) {
841 return false;
842 }
843 put(key, newValue);
844 return true;
845 }
846
847 /**
848 * Replaces the entry for the specified key only if it is
849 * currently mapped to some value.
850 *
851 * @implSpec
852 * The default implementation is equivalent to, for this {@code map}:
853 *
854 * <pre> {@code
855 * if (map.containsKey(key)) {
856 * return map.put(key, value);
857 * } else
858 * return null;
859 * }</pre>
860 *
861 * <p>The default implementation makes no guarantees about synchronization
862 * or atomicity properties of this method. Any implementation providing
863 * atomicity guarantees must override this method and document its
864 * concurrency properties.
865 *
866 * @param key key with which the specified value is associated
867 * @param value value to be associated with the specified key
868 * @return the previous value associated with the specified key, or
869 * {@code null} if there was no mapping for the key.
870 * (A {@code null} return can also indicate that the map
871 * previously associated {@code null} with the key,
872 * if the implementation supports null values.)
873 * @throws UnsupportedOperationException if the {@code put} operation
874 * is not supported by this map
875 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
876 * @throws ClassCastException if the class of the specified key or value
877 * prevents it from being stored in this map
878 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
879 * @throws NullPointerException if the specified key or value is null,
880 * and this map does not permit null keys or values
881 * @throws IllegalArgumentException if some property of the specified key
882 * or value prevents it from being stored in this map
883 * @since 1.8
884 */
885 default V replace(K key, V value) {
886 V curValue;
887 if (((curValue = get(key)) != null) || containsKey(key)) {
888 curValue = put(key, value);
889 }
890 return curValue;
891 }
892
893 /**
894 * If the specified key is not already associated with a value (or is mapped
895 * to {@code null}), attempts to compute its value using the given mapping
896 * function and enters it into this map unless {@code null}.
897 *
898 * <p>If the mapping function returns {@code null}, no mapping is recorded.
899 * If the mapping function itself throws an (unchecked) exception, the
900 * exception is rethrown, and no mapping is recorded. The most
901 * common usage is to construct a new object serving as an initial
902 * mapped value or memoized result, as in:
903 *
904 * <pre> {@code
905 * map.computeIfAbsent(key, k -> new Value(f(k)));
906 * }</pre>
907 *
908 * <p>Or to implement a multi-value map, {@code Map<K,Collection<V>>},
909 * supporting multiple values per key:
910 *
911 * <pre> {@code
912 * map.computeIfAbsent(key, k -> new HashSet<V>()).add(v);
913 * }</pre>
914 *
915 * <p>The mapping function should not modify this map during computation.
916 *
917 * @implSpec
918 * The default implementation is equivalent to the following steps for this
919 * {@code map}, then returning the current value or {@code null} if now
920 * absent:
921 *
922 * <pre> {@code
923 * if (map.get(key) == null) {
924 * V newValue = mappingFunction.apply(key);
925 * if (newValue != null)
926 * map.put(key, newValue);
927 * }
928 * }</pre>
929 *
930 * <p>The default implementation makes no guarantees about detecting if the
931 * mapping function modifies this map during computation and, if
932 * appropriate, reporting an error. Non-concurrent implementations should
933 * override this method and, on a best-effort basis, throw a
934 * {@code ConcurrentModificationException} if it is detected that the
935 * mapping function modifies this map during computation. Concurrent
936 * implementations should override this method and, on a best-effort basis,
937 * throw an {@code IllegalStateException} if it is detected that the
938 * mapping function modifies this map during computation and as a result
939 * computation would never complete.
940 *
941 * <p>The default implementation makes no guarantees about synchronization
942 * or atomicity properties of this method. Any implementation providing
943 * atomicity guarantees must override this method and document its
944 * concurrency properties. In particular, all implementations of
945 * subinterface {@link java.util.concurrent.ConcurrentMap} must document
946 * whether the mapping function is applied once atomically only if the value
947 * is not present.
948 *
949 * @param key key with which the specified value is to be associated
950 * @param mappingFunction the mapping function to compute a value
951 * @return the current (existing or computed) value associated with
952 * the specified key, or null if the computed value is null
953 * @throws NullPointerException if the specified key is null and
954 * this map does not support null keys, or the mappingFunction
955 * is null
956 * @throws UnsupportedOperationException if the {@code put} operation
957 * is not supported by this map
958 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
959 * @throws ClassCastException if the class of the specified key or value
960 * prevents it from being stored in this map
961 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
962 * @since 1.8
963 */
964 default V computeIfAbsent(K key,
965 Function<? super K, ? extends V> mappingFunction) {
966 Objects.requireNonNull(mappingFunction);
967 V v;
968 if ((v = get(key)) == null) {
969 V newValue;
970 if ((newValue = mappingFunction.apply(key)) != null) {
971 put(key, newValue);
972 return newValue;
973 }
974 }
975
976 return v;
977 }
978
979 /**
980 * If the value for the specified key is present and non-null, attempts to
981 * compute a new mapping given the key and its current mapped value.
982 *
983 * <p>If the remapping function returns {@code null}, the mapping is removed.
984 * If the remapping function itself throws an (unchecked) exception, the
985 * exception is rethrown, and the current mapping is left unchanged.
986 *
987 * <p>The remapping function should not modify this map during computation.
988 *
989 * @implSpec
990 * The default implementation is equivalent to performing the following
991 * steps for this {@code map}, then returning the current value or
992 * {@code null} if now absent:
993 *
994 * <pre> {@code
995 * if (map.get(key) != null) {
996 * V oldValue = map.get(key);
997 * V newValue = remappingFunction.apply(key, oldValue);
998 * if (newValue != null)
999 * map.put(key, newValue);
1000 * else
1001 * map.remove(key);
1002 * }
1003 * }</pre>
1004 *
1005 * <p>The default implementation makes no guarantees about detecting if the
1006 * remapping function modifies this map during computation and, if
1007 * appropriate, reporting an error. Non-concurrent implementations should
1008 * override this method and, on a best-effort basis, throw a
1009 * {@code ConcurrentModificationException} if it is detected that the
1010 * remapping function modifies this map during computation. Concurrent
1011 * implementations should override this method and, on a best-effort basis,
1012 * throw an {@code IllegalStateException} if it is detected that the
1013 * remapping function modifies this map during computation and as a result
1014 * computation would never complete.
1015 *
1016 * <p>The default implementation makes no guarantees about synchronization
1017 * or atomicity properties of this method. Any implementation providing
1018 * atomicity guarantees must override this method and document its
1019 * concurrency properties. In particular, all implementations of
1020 * subinterface {@link java.util.concurrent.ConcurrentMap} must document
1021 * whether the remapping function is applied once atomically only if the
1022 * value is not present.
1023 *
1024 * @param key key with which the specified value is to be associated
1025 * @param remappingFunction the remapping function to compute a value
1026 * @return the new value associated with the specified key, or null if none
1027 * @throws NullPointerException if the specified key is null and
1028 * this map does not support null keys, or the
1029 * remappingFunction is null
1030 * @throws UnsupportedOperationException if the {@code put} operation
1031 * is not supported by this map
1032 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
1033 * @throws ClassCastException if the class of the specified key or value
1034 * prevents it from being stored in this map
1035 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
1036 * @since 1.8
1037 */
1038 default V computeIfPresent(K key,
1039 BiFunction<? super K, ? super V, ? extends V> remappingFunction) {
1040 Objects.requireNonNull(remappingFunction);
1041 V oldValue;
1042 if ((oldValue = get(key)) != null) {
1043 V newValue = remappingFunction.apply(key, oldValue);
1044 if (newValue != null) {
1045 put(key, newValue);
1046 return newValue;
1047 } else {
1048 remove(key);
1049 return null;
1050 }
1051 } else {
1052 return null;
1053 }
1054 }
1055
1056 /**
1057 * Attempts to compute a mapping for the specified key and its current
1058 * mapped value (or {@code null} if there is no current mapping). For
1059 * example, to either create or append a {@code String} msg to a value
1060 * mapping:
1061 *
1062 * <pre> {@code
1063 * map.compute(key, (k, v) -> (v == null) ? msg : v.concat(msg))}</pre>
1064 * (Method {@link #merge merge()} is often simpler to use for such purposes.)
1065 *
1066 * <p>If the remapping function returns {@code null}, the mapping is removed
1067 * (or remains absent if initially absent). If the remapping function
1068 * itself throws an (unchecked) exception, the exception is rethrown, and
1069 * the current mapping is left unchanged.
1070 *
1071 * <p>The remapping function should not modify this map during computation.
1072 *
1073 * @implSpec
1074 * The default implementation is equivalent to performing the following
1075 * steps for this {@code map}, then returning the current value or
1076 * {@code null} if absent:
1077 *
1078 * <pre> {@code
1079 * V oldValue = map.get(key);
1080 * V newValue = remappingFunction.apply(key, oldValue);
1081 * if (oldValue != null ) {
1082 * if (newValue != null)
1083 * map.put(key, newValue);
1084 * else
1085 * map.remove(key);
1086 * } else {
1087 * if (newValue != null)
1088 * map.put(key, newValue);
1089 * else
1090 * return null;
1091 * }
1092 * }</pre>
1093 *
1094 * <p>The default implementation makes no guarantees about detecting if the
1095 * remapping function modifies this map during computation and, if
1096 * appropriate, reporting an error. Non-concurrent implementations should
1097 * override this method and, on a best-effort basis, throw a
1098 * {@code ConcurrentModificationException} if it is detected that the
1099 * remapping function modifies this map during computation. Concurrent
1100 * implementations should override this method and, on a best-effort basis,
1101 * throw an {@code IllegalStateException} if it is detected that the
1102 * remapping function modifies this map during computation and as a result
1103 * computation would never complete.
1104 *
1105 * <p>The default implementation makes no guarantees about synchronization
1106 * or atomicity properties of this method. Any implementation providing
1107 * atomicity guarantees must override this method and document its
1108 * concurrency properties. In particular, all implementations of
1109 * subinterface {@link java.util.concurrent.ConcurrentMap} must document
1110 * whether the remapping function is applied once atomically only if the
1111 * value is not present.
1112 *
1113 * @param key key with which the specified value is to be associated
1114 * @param remappingFunction the remapping function to compute a value
1115 * @return the new value associated with the specified key, or null if none
1116 * @throws NullPointerException if the specified key is null and
1117 * this map does not support null keys, or the
1118 * remappingFunction is null
1119 * @throws UnsupportedOperationException if the {@code put} operation
1120 * is not supported by this map
1121 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
1122 * @throws ClassCastException if the class of the specified key or value
1123 * prevents it from being stored in this map
1124 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
1125 * @since 1.8
1126 */
1127 default V compute(K key,
1128 BiFunction<? super K, ? super V, ? extends V> remappingFunction) {
1129 Objects.requireNonNull(remappingFunction);
1130 V oldValue = get(key);
1131
1132 V newValue = remappingFunction.apply(key, oldValue);
1133 if (newValue == null) {
1134 // delete mapping
1135 if (oldValue != null || containsKey(key)) {
1136 // something to remove
1137 remove(key);
1138 return null;
1139 } else {
1140 // nothing to do. Leave things as they were.
1141 return null;
1142 }
1143 } else {
1144 // add or replace old mapping
1145 put(key, newValue);
1146 return newValue;
1147 }
1148 }
1149
1150 /**
1151 * If the specified key is not already associated with a value or is
1152 * associated with null, associates it with the given non-null value.
1153 * Otherwise, replaces the associated value with the results of the given
1154 * remapping function, or removes if the result is {@code null}. This
1155 * method may be of use when combining multiple mapped values for a key.
1156 * For example, to either create or append a {@code String msg} to a
1157 * value mapping:
1158 *
1159 * <pre> {@code
1160 * map.merge(key, msg, String::concat)
1161 * }</pre>
1162 *
1163 * <p>If the remapping function returns {@code null}, the mapping is removed.
1164 * If the remapping function itself throws an (unchecked) exception, the
1165 * exception is rethrown, and the current mapping is left unchanged.
1166 *
1167 * <p>The remapping function should not modify this map during computation.
1168 *
1169 * @implSpec
1170 * The default implementation is equivalent to performing the following
1171 * steps for this {@code map}, then returning the current value or
1172 * {@code null} if absent:
1173 *
1174 * <pre> {@code
1175 * V oldValue = map.get(key);
1176 * V newValue = (oldValue == null) ? value :
1177 * remappingFunction.apply(oldValue, value);
1178 * if (newValue == null)
1179 * map.remove(key);
1180 * else
1181 * map.put(key, newValue);
1182 * }</pre>
1183 *
1184 * <p>The default implementation makes no guarantees about detecting if the
1185 * remapping function modifies this map during computation and, if
1186 * appropriate, reporting an error. Non-concurrent implementations should
1187 * override this method and, on a best-effort basis, throw a
1188 * {@code ConcurrentModificationException} if it is detected that the
1189 * remapping function modifies this map during computation. Concurrent
1190 * implementations should override this method and, on a best-effort basis,
1191 * throw an {@code IllegalStateException} if it is detected that the
1192 * remapping function modifies this map during computation and as a result
1193 * computation would never complete.
1194 *
1195 * <p>The default implementation makes no guarantees about synchronization
1196 * or atomicity properties of this method. Any implementation providing
1197 * atomicity guarantees must override this method and document its
1198 * concurrency properties. In particular, all implementations of
1199 * subinterface {@link java.util.concurrent.ConcurrentMap} must document
1200 * whether the remapping function is applied once atomically only if the
1201 * value is not present.
1202 *
1203 * @param key key with which the resulting value is to be associated
1204 * @param value the non-null value to be merged with the existing value
1205 * associated with the key or, if no existing value or a null value
1206 * is associated with the key, to be associated with the key
1207 * @param remappingFunction the remapping function to recompute a value if
1208 * present
1209 * @return the new value associated with the specified key, or null if no
1210 * value is associated with the key
1211 * @throws UnsupportedOperationException if the {@code put} operation
1212 * is not supported by this map
1213 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
1214 * @throws ClassCastException if the class of the specified key or value
1215 * prevents it from being stored in this map
1216 * (<a href="{@docRoot}/java/util/Collection.html#optional-restrictions">optional</a>)
1217 * @throws NullPointerException if the specified key is null and this map
1218 * does not support null keys or the value or remappingFunction is
1219 * null
1220 * @since 1.8
1221 */
1222 default V merge(K key, V value,
1223 BiFunction<? super V, ? super V, ? extends V> remappingFunction) {
1224 Objects.requireNonNull(remappingFunction);
1225 Objects.requireNonNull(value);
1226 V oldValue = get(key);
1227 V newValue = (oldValue == null) ? value :
1228 remappingFunction.apply(oldValue, value);
1229 if (newValue == null) {
1230 remove(key);
1231 } else {
1232 put(key, newValue);
1233 }
1234 return newValue;
1235 }
1236 }