OLD | NEW |
1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file |
2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
4 | 4 |
5 part of dart.collection; | 5 part of dart.collection; |
6 | 6 |
7 /** Default function for equality comparison in customized HashMaps */ | 7 /** Default function for equality comparison in customized HashMaps */ |
8 bool _defaultEquals(a, b) => a == b; | 8 bool _defaultEquals(a, b) => a == b; |
9 /** Default function for hash-code computation in customized HashMaps */ | 9 /** Default function for hash-code computation in customized HashMaps */ |
10 int _defaultHashCode(a) => a.hashCode; | 10 int _defaultHashCode(a) => a.hashCode; |
11 | 11 |
| 12 /** Type of custom equality function */ |
| 13 typedef bool _Equality<K>(K a, K b); |
| 14 /** Type of custom hash code function. */ |
| 15 typedef int _Hasher<K>(K object); |
| 16 |
12 /** | 17 /** |
13 * A hash-table based implementation of [Map]. | 18 * A hash-table based implementation of [Map]. |
14 * | 19 * |
15 * The keys of a `HashMap` must have consistent [Object.operator==] | 20 * The keys of a `HashMap` must have consistent [Object.operator==] |
16 * and [Object.hashCode] implementations. This means that the `==` operator | 21 * and [Object.hashCode] implementations. This means that the `==` operator |
17 * must define a stable equivalence relation on the keys (reflexive, | 22 * must define a stable equivalence relation on the keys (reflexive, |
18 * anti-symmetric, transitive, and consistent over time), and that `hashCode` | 23 * anti-symmetric, transitive, and consistent over time), and that `hashCode` |
19 * must be the same for objects that are considered equal by `==`. | 24 * must be the same for objects that are considered equal by `==`. |
20 * | 25 * |
21 * The map allows `null` as a key. | 26 * The map allows `null` as a key. |
22 */ | 27 */ |
23 class HashMap<K, V> implements Map<K, V> { | 28 abstract class HashMap<K, V> implements Map<K, V> { |
24 /** | 29 /** |
25 * Creates a hash-table based [Map]. | 30 * Creates a hash-table based [Map]. |
26 * | 31 * |
27 * The created map is not ordered in any way. When iterating the keys or | 32 * The created map is not ordered in any way. When iterating the keys or |
28 * values, the iteration order is unspecified except that it will stay the | 33 * values, the iteration order is unspecified except that it will stay the |
29 * same as long as the map isn't changed. | 34 * same as long as the map isn't changed. |
30 * | 35 * |
31 * If [equals] is provided, it is used to compare the keys in the table with | 36 * If [equals] is provided, it is used to compare the keys in the table with |
32 * new keys. If [equals] is omitted, the key's own [Object.operator==] is used | 37 * new keys. If [equals] is omitted, the key's own [Object.operator==] is used |
33 * instead. | 38 * instead. |
34 * | 39 * |
35 * Similar, if [hashCode] is provided, it is used to produce a hash value | 40 * Similar, if [hashCode] is provided, it is used to produce a hash value |
36 * for keys in order to place them in the hash table. If it is omitted, the | 41 * for keys in order to place them in the hash table. If it is omitted, the |
37 * key's own [Object.hashCode] is used. | 42 * key's own [Object.hashCode] is used. |
38 * | 43 * |
39 * The used `equals` and `hashCode` method should always be consistent, | 44 * The used `equals` and `hashCode` method should always be consistent, |
40 * so that if `equals(a, b)` then `hashCode(a) == hashCode(b)`. The hash | 45 * so that if `equals(a, b)` then `hashCode(a) == hashCode(b)`. The hash |
41 * of an object, or what it compares equal to, should not change while the | 46 * of an object, or what it compares equal to, should not change while the |
42 * object is in the table. If it does change, the result is unpredictable. | 47 * object is in the table. If it does change, the result is unpredictable. |
| 48 * |
| 49 * It is generally the case that if you supply one of [equals] and [hashCode], |
| 50 * you also want to supply the other. The only common exception is to pass |
| 51 * [identical] as the equality and use the default hash code. |
43 */ | 52 */ |
44 factory HashMap({bool equals(K key1, K key2), int hashCode(K key)}) { | 53 external factory HashMap({bool equals(K key1, K key2), int hashCode(K key)}); |
45 if (equals != null || hashCode != null) { | |
46 if (equals == null) { | |
47 equals = _defaultEquals; | |
48 } else if (hashCode == null) { | |
49 hashCode = _defaultHashCode; | |
50 } | |
51 // Create new CustomHashMap<K, V>(equals, hashCode). | |
52 throw new UnimplementedError("Not implemented yet"); | |
53 } | |
54 return new HashMap<K, V>._internal(); | |
55 } | |
56 | |
57 /** Creates an empty `HashMap` with the default equals and hashCode. */ | |
58 external HashMap._internal(); | |
59 | 54 |
60 /** | 55 /** |
61 * Creates a [HashMap] that contains all key value pairs of [other]. | 56 * Creates a [HashMap] that contains all key value pairs of [other]. |
62 */ | 57 */ |
63 factory HashMap.from(Map<K, V> other) { | 58 factory HashMap.from(Map<K, V> other) { |
64 return new HashMap<K, V>()..addAll(other); | 59 return new HashMap<K, V>()..addAll(other); |
65 } | 60 } |
66 | 61 |
67 /** | 62 /** |
68 * Creates a [HashMap] where the keys and values are computed from the | 63 * Creates a [HashMap] where the keys and values are computed from the |
(...skipping 24 matching lines...) Expand all Loading... |
93 * If [keys] contains the same object multiple times, the last occurrence | 88 * If [keys] contains the same object multiple times, the last occurrence |
94 * overwrites the previous value. | 89 * overwrites the previous value. |
95 * | 90 * |
96 * It is an error if the two [Iterable]s don't have the same length. | 91 * It is an error if the two [Iterable]s don't have the same length. |
97 */ | 92 */ |
98 factory HashMap.fromIterables(Iterable<K> keys, Iterable<V> values) { | 93 factory HashMap.fromIterables(Iterable<K> keys, Iterable<V> values) { |
99 HashMap<K, V> map = new HashMap<K, V>(); | 94 HashMap<K, V> map = new HashMap<K, V>(); |
100 Maps._fillMapWithIterables(map, keys, values); | 95 Maps._fillMapWithIterables(map, keys, values); |
101 return map; | 96 return map; |
102 } | 97 } |
103 | |
104 external int get length; | |
105 external bool get isEmpty; | |
106 external bool get isNotEmpty; | |
107 | |
108 external Iterable<K> get keys; | |
109 external Iterable<V> get values; | |
110 | |
111 external bool containsKey(Object key); | |
112 external bool containsValue(Object value); | |
113 | |
114 external void addAll(Map<K, V> other); | |
115 | |
116 external V operator [](Object key); | |
117 external void operator []=(K key, V value); | |
118 | |
119 external V putIfAbsent(K key, V ifAbsent()); | |
120 | |
121 external V remove(Object key); | |
122 external void clear(); | |
123 | |
124 external void forEach(void action(K key, V value)); | |
125 | |
126 String toString() => Maps.mapToString(this); | |
127 } | 98 } |
OLD | NEW |