Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(313)

Side by Side Diff: tests/corelib_strong/map_test.dart

Issue 2990903002: Migrated test block 16 to Dart 2.0. (Closed)
Patch Set: Changed useIntegerKeys to a named parameter Created 3 years, 4 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « tests/corelib_strong/map_remove_test.dart ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
(Empty)
1 // Copyright (c) 2011, the Dart project authors. Please see the AUTHORS file
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.
4
5 library map_test;
6
7 import "package:expect/expect.dart";
8 import 'dart:collection';
9 import 'dart:convert' show JSON;
10
11 Map newJsonMap() => JSON.decode('{}');
12 Map newJsonMapCustomReviver() =>
13 JSON.decode('{}', reviver: (key, value) => value);
14
15 void main() {
16 test(new HashMap());
17 test(new LinkedHashMap());
18 test(new SplayTreeMap());
19 test(new SplayTreeMap(Comparable.compare));
20 test(new MapView(new HashMap()));
21 test(new MapView(new SplayTreeMap()));
22 test(new MapBaseMap());
23 test(new MapMixinMap());
24 test(newJsonMap());
25 test(newJsonMapCustomReviver());
26 testLinkedHashMap();
27 testMapLiteral();
28 testNullValue();
29 testTypes();
30
31 testWeirdStringKeys(new Map());
32 testWeirdStringKeys(new Map<String, String>());
33 testWeirdStringKeys(new HashMap());
34 testWeirdStringKeys(new HashMap<String, String>());
35 testWeirdStringKeys(new LinkedHashMap());
36 testWeirdStringKeys(new LinkedHashMap<String, String>());
37 testWeirdStringKeys(new SplayTreeMap());
38 testWeirdStringKeys(new SplayTreeMap<String, String>());
39 testWeirdStringKeys(new MapBaseMap<String, String>());
40 testWeirdStringKeys(new MapMixinMap<String, String>());
41 testWeirdStringKeys(newJsonMap());
42 testWeirdStringKeys(newJsonMapCustomReviver());
43
44 testNumericKeys(new Map());
45 testNumericKeys(new Map<num, String>());
46 testNumericKeys(new HashMap());
47 testNumericKeys(new HashMap<num, String>());
48 testNumericKeys(new HashMap.identity());
49 testNumericKeys(new HashMap<num, String>.identity());
50 testNumericKeys(new LinkedHashMap());
51 testNumericKeys(new LinkedHashMap<num, String>());
52 testNumericKeys(new LinkedHashMap.identity());
53 testNumericKeys(new LinkedHashMap<num, String>.identity());
54 testNumericKeys(new MapBaseMap<num, String>());
55 testNumericKeys(new MapMixinMap<num, String>());
56 testNumericKeys(newJsonMap());
57 testNumericKeys(newJsonMapCustomReviver());
58
59 testNaNKeys(new Map());
60 testNaNKeys(new Map<num, String>());
61 testNaNKeys(new HashMap());
62 testNaNKeys(new HashMap<num, String>());
63 testNaNKeys(new LinkedHashMap());
64 testNaNKeys(new LinkedHashMap<num, String>());
65 testNaNKeys(new MapBaseMap<num, String>());
66 testNaNKeys(new MapMixinMap<num, String>());
67 testNaNKeys(newJsonMap());
68 testNaNKeys(newJsonMapCustomReviver());
69 // Identity maps fail the NaN-keys tests because the test assumes that
70 // NaN is not equal to NaN.
71
72 testIdentityMap(new Map.identity());
73 testIdentityMap(new HashMap.identity());
74 testIdentityMap(new LinkedHashMap.identity());
75 testIdentityMap(new HashMap(equals: identical, hashCode: identityHashCode));
76 testIdentityMap(
77 new LinkedHashMap(equals: identical, hashCode: identityHashCode));
78 testIdentityMap(new HashMap(
79 equals: (x, y) => identical(x, y), hashCode: (x) => identityHashCode(x)));
80 testIdentityMap(new LinkedHashMap(
81 equals: (x, y) => identical(x, y), hashCode: (x) => identityHashCode(x)));
82
83 testCustomMap(new HashMap(
84 equals: myEquals,
85 hashCode: myHashCode,
86 isValidKey: (v) => v is Customer));
87 testCustomMap(new LinkedHashMap(
88 equals: myEquals,
89 hashCode: myHashCode,
90 isValidKey: (v) => v is Customer));
91 testCustomMap(
92 new HashMap<Customer, dynamic>(equals: myEquals, hashCode: myHashCode));
93
94 testCustomMap(new LinkedHashMap<Customer, dynamic>(
95 equals: myEquals, hashCode: myHashCode));
96
97 testIterationOrder(new LinkedHashMap());
98 testIterationOrder(new LinkedHashMap.identity());
99 testIterationOrder(newJsonMap());
100 testIterationOrder(newJsonMapCustomReviver());
101
102 testOtherKeys(new SplayTreeMap<int, int>());
103 testOtherKeys(
104 new SplayTreeMap<int, int>((int a, int b) => a - b, (v) => v is int));
105 testOtherKeys(new SplayTreeMap((int a, int b) => a - b, (v) => v is int));
106 testOtherKeys(new HashMap<int, int>());
107 testOtherKeys(new HashMap<int, int>.identity());
108 testOtherKeys(new HashMap<int, int>(
109 hashCode: (v) => v.hashCode, isValidKey: (v) => v is int));
110 testOtherKeys(new HashMap(
111 equals: (int x, int y) => x == y,
112 hashCode: (int v) => v.hashCode,
113 isValidKey: (v) => v is int));
114 testOtherKeys(new LinkedHashMap<int, int>());
115 testOtherKeys(new LinkedHashMap<int, int>.identity());
116 testOtherKeys(new LinkedHashMap<int, int>(
117 hashCode: (v) => v.hashCode, isValidKey: (v) => v is int));
118 testOtherKeys(new LinkedHashMap(
119 equals: (int x, int y) => x == y,
120 hashCode: (int v) => v.hashCode,
121 isValidKey: (v) => v is int));
122 testOtherKeys(new MapBaseMap<int, int>());
123 testOtherKeys(new MapMixinMap<int, int>());
124 testOtherKeys(newJsonMap());
125 testOtherKeys(newJsonMapCustomReviver());
126
127 testUnmodifiableMap(const {1: 37});
128 testUnmodifiableMap(new UnmodifiableMapView({1: 37}));
129 testUnmodifiableMap(new UnmodifiableMapBaseMap([1, 37]));
130
131 testFrom();
132 }
133
134 void test(Map map) {
135 testDeletedElement(map);
136 testMap(map, 1, 2, 3, 4, 5, 6, 7, 8);
137 map.clear();
138 testMap(map, "value1", "value2", "value3", "value4", "value5", "value6",
139 "value7", "value8");
140 }
141
142 void testLinkedHashMap() {
143 LinkedHashMap map = new LinkedHashMap();
144 Expect.equals(false, map.containsKey(1));
145 map[1] = 1;
146 map[1] = 2;
147 testLength(1, map);
148 }
149
150 void testMap(Map map, key1, key2, key3, key4, key5, key6, key7, key8) {
151 int value1 = 10;
152 int value2 = 20;
153 int value3 = 30;
154 int value4 = 40;
155 int value5 = 50;
156 int value6 = 60;
157 int value7 = 70;
158 int value8 = 80;
159
160 testLength(0, map);
161
162 map[key1] = value1;
163 Expect.equals(value1, map[key1]);
164 map[key1] = value2;
165 Expect.equals(false, map.containsKey(key2));
166 testLength(1, map);
167
168 map[key1] = value1;
169 Expect.equals(value1, map[key1]);
170 // Add enough entries to make sure the table grows.
171 map[key2] = value2;
172 Expect.equals(value2, map[key2]);
173 testLength(2, map);
174 map[key3] = value3;
175 Expect.equals(value2, map[key2]);
176 Expect.equals(value3, map[key3]);
177 map[key4] = value4;
178 Expect.equals(value3, map[key3]);
179 Expect.equals(value4, map[key4]);
180 map[key5] = value5;
181 Expect.equals(value4, map[key4]);
182 Expect.equals(value5, map[key5]);
183 map[key6] = value6;
184 Expect.equals(value5, map[key5]);
185 Expect.equals(value6, map[key6]);
186 map[key7] = value7;
187 Expect.equals(value6, map[key6]);
188 Expect.equals(value7, map[key7]);
189 map[key8] = value8;
190 Expect.equals(value1, map[key1]);
191 Expect.equals(value2, map[key2]);
192 Expect.equals(value3, map[key3]);
193 Expect.equals(value4, map[key4]);
194 Expect.equals(value5, map[key5]);
195 Expect.equals(value6, map[key6]);
196 Expect.equals(value7, map[key7]);
197 Expect.equals(value8, map[key8]);
198 testLength(8, map);
199
200 map.remove(key4);
201 Expect.equals(false, map.containsKey(key4));
202 testLength(7, map);
203
204 // Test clearing the table.
205 map.clear();
206 testLength(0, map);
207 Expect.equals(false, map.containsKey(key1));
208 Expect.equals(false, map.containsKey(key2));
209 Expect.equals(false, map.containsKey(key3));
210 Expect.equals(false, map.containsKey(key4));
211 Expect.equals(false, map.containsKey(key5));
212 Expect.equals(false, map.containsKey(key6));
213 Expect.equals(false, map.containsKey(key7));
214 Expect.equals(false, map.containsKey(key8));
215
216 // Test adding and removing again.
217 map[key1] = value1;
218 Expect.equals(value1, map[key1]);
219 testLength(1, map);
220 map[key2] = value2;
221 Expect.equals(value2, map[key2]);
222 testLength(2, map);
223 map[key3] = value3;
224 Expect.equals(value3, map[key3]);
225 map.remove(key3);
226 testLength(2, map);
227 map[key4] = value4;
228 Expect.equals(value4, map[key4]);
229 map.remove(key4);
230 testLength(2, map);
231 map[key5] = value5;
232 Expect.equals(value5, map[key5]);
233 map.remove(key5);
234 testLength(2, map);
235 map[key6] = value6;
236 Expect.equals(value6, map[key6]);
237 map.remove(key6);
238 testLength(2, map);
239 map[key7] = value7;
240 Expect.equals(value7, map[key7]);
241 map.remove(key7);
242 testLength(2, map);
243 map[key8] = value8;
244 Expect.equals(value8, map[key8]);
245 map.remove(key8);
246 testLength(2, map);
247
248 Expect.equals(true, map.containsKey(key1));
249 Expect.equals(true, map.containsValue(value1));
250
251 // Test Map.forEach.
252 Map otherMap = new Map();
253 void testForEachMap(key, value) {
254 otherMap[key] = value;
255 }
256
257 map.forEach(testForEachMap);
258 Expect.equals(true, otherMap.containsKey(key1));
259 Expect.equals(true, otherMap.containsKey(key2));
260 Expect.equals(true, otherMap.containsValue(value1));
261 Expect.equals(true, otherMap.containsValue(value2));
262 Expect.equals(2, otherMap.length);
263
264 otherMap.clear();
265 Expect.equals(0, otherMap.length);
266
267 // Test Collection.keys.
268 void testForEachCollection(value) {
269 otherMap[value] = value;
270 }
271
272 Iterable keys = map.keys;
273 keys.forEach(testForEachCollection);
274 Expect.equals(true, otherMap.containsKey(key1));
275 Expect.equals(true, otherMap.containsKey(key2));
276 Expect.equals(true, otherMap.containsValue(key1));
277 Expect.equals(true, otherMap.containsValue(key2));
278 Expect.equals(true, !otherMap.containsKey(value1));
279 Expect.equals(true, !otherMap.containsKey(value2));
280 Expect.equals(true, !otherMap.containsValue(value1));
281 Expect.equals(true, !otherMap.containsValue(value2));
282 Expect.equals(2, otherMap.length);
283 otherMap.clear();
284 Expect.equals(0, otherMap.length);
285
286 // Test Collection.values.
287 Iterable values = map.values;
288 values.forEach(testForEachCollection);
289 Expect.equals(true, !otherMap.containsKey(key1));
290 Expect.equals(true, !otherMap.containsKey(key2));
291 Expect.equals(true, !otherMap.containsValue(key1));
292 Expect.equals(true, !otherMap.containsValue(key2));
293 Expect.equals(true, otherMap.containsKey(value1));
294 Expect.equals(true, otherMap.containsKey(value2));
295 Expect.equals(true, otherMap.containsValue(value1));
296 Expect.equals(true, otherMap.containsValue(value2));
297 Expect.equals(2, otherMap.length);
298 otherMap.clear();
299 Expect.equals(0, otherMap.length);
300
301 // Test Map.putIfAbsent.
302 map.clear();
303 Expect.equals(false, map.containsKey(key1));
304 map.putIfAbsent(key1, () => 10);
305 Expect.equals(true, map.containsKey(key1));
306 Expect.equals(10, map[key1]);
307 Expect.equals(10, map.putIfAbsent(key1, () => 11));
308
309 // Test Map.addAll.
310 map.clear();
311 otherMap.clear();
312 otherMap[99] = 1;
313 otherMap[50] = 50;
314 otherMap[1] = 99;
315 map.addAll(otherMap);
316 Expect.equals(3, map.length);
317 Expect.equals(1, map[99]);
318 Expect.equals(50, map[50]);
319 Expect.equals(99, map[1]);
320 otherMap[50] = 42;
321 map.addAll(new HashMap.from(otherMap));
322 Expect.equals(3, map.length);
323 Expect.equals(1, map[99]);
324 Expect.equals(42, map[50]);
325 Expect.equals(99, map[1]);
326 otherMap[99] = 7;
327 map.addAll(new SplayTreeMap.from(otherMap));
328 Expect.equals(3, map.length);
329 Expect.equals(7, map[99]);
330 Expect.equals(42, map[50]);
331 Expect.equals(99, map[1]);
332 otherMap.remove(99);
333 map[99] = 0;
334 map.addAll(otherMap);
335 Expect.equals(3, map.length);
336 Expect.equals(0, map[99]);
337 Expect.equals(42, map[50]);
338 Expect.equals(99, map[1]);
339 map.clear();
340 otherMap.clear();
341 map.addAll(otherMap);
342 Expect.equals(0, map.length);
343 }
344
345 void testDeletedElement(Map map) {
346 map.clear();
347 for (int i = 0; i < 100; i++) {
348 map[1] = 2;
349 testLength(1, map);
350 map.remove(1);
351 testLength(0, map);
352 }
353 testLength(0, map);
354 }
355
356 void testMapLiteral() {
357 Map m = {"a": 1, "b": 2, "c": 3};
358 Expect.equals(3, m.length);
359 int sum = 0;
360 m.forEach((a, b) {
361 sum += b;
362 });
363 Expect.equals(6, sum);
364
365 List values = m.keys.toList();
366 Expect.equals(3, values.length);
367 String first = values[0];
368 String second = values[1];
369 String third = values[2];
370 String all = "${first}${second}${third}";
371 Expect.equals(3, all.length);
372 Expect.equals(true, all.contains("a", 0));
373 Expect.equals(true, all.contains("b", 0));
374 Expect.equals(true, all.contains("c", 0));
375 }
376
377 void testNullValue() {
378 Map m = {"a": 1, "b": null, "c": 3};
379
380 Expect.equals(null, m["b"]);
381 Expect.equals(true, m.containsKey("b"));
382 Expect.equals(3, m.length);
383
384 m["a"] = null;
385 m["c"] = null;
386 Expect.equals(null, m["a"]);
387 Expect.equals(true, m.containsKey("a"));
388 Expect.equals(null, m["c"]);
389 Expect.equals(true, m.containsKey("c"));
390 Expect.equals(3, m.length);
391
392 m.remove("a");
393 Expect.equals(2, m.length);
394 Expect.equals(null, m["a"]);
395 Expect.equals(false, m.containsKey("a"));
396 }
397
398 void testTypes() {
399 testMap(Map<num, String> map) {
400 Expect.isTrue(map is Map<num, String>);
401 Expect.isTrue(map is! Map<String, dynamic>);
402 Expect.isTrue(map is! Map<dynamic, int>);
403
404 // Use with properly typed keys and values.
405 map[42] = "text1";
406 map[43] = "text2";
407 map[42] = "text3";
408 Expect.equals("text3", map.remove(42));
409 Expect.equals(null, map[42]);
410 map[42] = "text4";
411
412 // Ensure that "containsKey", "containsValue" and "remove"
413 // accepts any object.
414 for (var object in [true, null, new Object()]) {
415 Expect.isFalse(map.containsKey(object));
416 Expect.isFalse(map.containsValue(object));
417 Expect.isNull(map.remove(object));
418 Expect.isNull(map[object]);
419 }
420 }
421
422 testMap(new HashMap<int, String>());
423 testMap(new LinkedHashMap<int, String>());
424 testMap(new SplayTreeMap<int, String>());
425 testMap(new SplayTreeMap<int, String>(Comparable.compare));
426 testMap(new SplayTreeMap<int, String>((int a, int b) => a.compareTo(b)));
427 testMap(new HashMap<num, String>());
428 testMap(new LinkedHashMap<num, String>());
429 testMap(new SplayTreeMap<num, String>());
430 testMap(new SplayTreeMap<num, String>(Comparable.compare));
431 testMap(new SplayTreeMap<num, String>((num a, num b) => a.compareTo(b)));
432 }
433
434 void testWeirdStringKeys(Map map) {
435 // Test weird keys.
436 var weirdKeys = const [
437 'hasOwnProperty',
438 'constructor',
439 'toLocaleString',
440 'propertyIsEnumerable',
441 '__defineGetter__',
442 '__defineSetter__',
443 '__lookupGetter__',
444 '__lookupSetter__',
445 'isPrototypeOf',
446 'toString',
447 'valueOf',
448 '__proto__',
449 '__count__',
450 '__parent__',
451 ''
452 ];
453 Expect.isTrue(map.isEmpty);
454 for (var key in weirdKeys) {
455 Expect.isFalse(map.containsKey(key));
456 Expect.equals(null, map[key]);
457 var value = 'value:$key';
458 map[key] = value;
459 Expect.isTrue(map.containsKey(key));
460 Expect.equals(value, map[key]);
461 Expect.equals(value, map.remove(key));
462 Expect.isFalse(map.containsKey(key));
463 Expect.equals(null, map[key]);
464 }
465 Expect.isTrue(map.isEmpty);
466 }
467
468 void testNumericKeys(Map map) {
469 var numericKeys = const [
470 double.INFINITY,
471 double.NEGATIVE_INFINITY,
472 0,
473 0.0,
474 -0.0
475 ];
476
477 Expect.isTrue(map.isEmpty);
478 for (var key in numericKeys) {
479 Expect.isFalse(map.containsKey(key));
480 Expect.equals(null, map[key]);
481 var value = 'value:$key';
482 map[key] = value;
483 Expect.isTrue(map.containsKey(key));
484 Expect.equals(value, map[key]);
485 Expect.equals(value, map.remove(key));
486 Expect.isFalse(map.containsKey(key));
487 Expect.equals(null, map[key]);
488 }
489 Expect.isTrue(map.isEmpty);
490 }
491
492 void testNaNKeys(Map map) {
493 Expect.isTrue(map.isEmpty);
494 // Test NaN.
495 var nan = double.NAN;
496 Expect.isFalse(map.containsKey(nan));
497 Expect.equals(null, map[nan]);
498
499 map[nan] = 'value:0';
500 Expect.isFalse(map.containsKey(nan));
501 Expect.equals(null, map[nan]);
502 testLength(1, map);
503
504 map[nan] = 'value:1';
505 Expect.isFalse(map.containsKey(nan));
506 Expect.equals(null, map[nan]);
507 testLength(2, map);
508
509 Expect.equals(null, map.remove(nan));
510 testLength(2, map);
511
512 var count = 0;
513 map.forEach((key, value) {
514 if (key.isNaN) count++;
515 });
516 Expect.equals(2, count);
517
518 map.clear();
519 Expect.isTrue(map.isEmpty);
520 }
521
522 void testLength(int length, Map map) {
523 Expect.equals(length, map.length);
524 Expect.equals(length, map.keys.length);
525 Expect.equals(length, map.values.length);
526 // Check being-empty.
527 var ifEmpty = (length == 0) ? Expect.isTrue : Expect.isFalse;
528 var ifNotEmpty = (length != 0) ? Expect.isTrue : Expect.isFalse;
529 ifEmpty(map.isEmpty);
530 ifNotEmpty(map.isNotEmpty);
531 ifEmpty(map.keys.isEmpty);
532 ifNotEmpty(map.keys.isNotEmpty);
533 ifEmpty(map.values.isEmpty);
534 ifNotEmpty(map.values.isNotEmpty);
535 // Test key/value iterators match their isEmpty/isNotEmpty.
536 ifNotEmpty(map.keys.iterator.moveNext());
537 ifNotEmpty(map.values.iterator.moveNext());
538 if (length == 0) {
539 for (var k in map.keys) Expect.fail("contains key when iterating: $k");
540 for (var v in map.values) Expect.fail("contains values when iterating: $v");
541 }
542 }
543
544 testIdentityMap(Map map) {
545 Expect.isTrue(map.isEmpty);
546
547 var nan = double.NAN;
548 // TODO(11551): Remove guard when dart2js makes identical(NaN, NaN) true.
549 if (identical(nan, nan)) {
550 map[nan] = 42;
551 testLength(1, map);
552 Expect.isTrue(map.containsKey(nan));
553 Expect.equals(42, map[nan]);
554 map[nan] = 37;
555 testLength(1, map);
556 Expect.equals(37, map[nan]);
557 Expect.equals(37, map.remove(nan));
558 testLength(0, map);
559 }
560
561 Vampire v1 = const Vampire(1);
562 Vampire v2 = const Vampire(2);
563 Expect.isFalse(v1 == v1);
564 Expect.isFalse(v2 == v2);
565 Expect.isTrue(v2 == v1); // Snob!
566
567 map[v1] = 1;
568 map[v2] = 2;
569 testLength(2, map);
570
571 Expect.isTrue(map.containsKey(v1));
572 Expect.isTrue(map.containsKey(v2));
573
574 Expect.equals(1, map[v1]);
575 Expect.equals(2, map[v2]);
576
577 Expect.equals(1, map.remove(v1));
578 testLength(1, map);
579 Expect.isFalse(map.containsKey(v1));
580 Expect.isTrue(map.containsKey(v2));
581
582 Expect.isNull(map.remove(v1));
583 Expect.equals(2, map.remove(v2));
584 testLength(0, map);
585
586 var eq01 = new Equalizer(0);
587 var eq02 = new Equalizer(0);
588 var eq11 = new Equalizer(1);
589 var eq12 = new Equalizer(1);
590 // Sanity.
591 Expect.equals(eq01, eq02);
592 Expect.equals(eq02, eq01);
593 Expect.equals(eq11, eq12);
594 Expect.equals(eq12, eq11);
595 Expect.notEquals(eq01, eq11);
596 Expect.notEquals(eq01, eq12);
597 Expect.notEquals(eq02, eq11);
598 Expect.notEquals(eq02, eq12);
599 Expect.notEquals(eq11, eq01);
600 Expect.notEquals(eq11, eq02);
601 Expect.notEquals(eq12, eq01);
602 Expect.notEquals(eq12, eq02);
603
604 map[eq01] = 0;
605 map[eq02] = 1;
606 map[eq11] = 2;
607 map[eq12] = 3;
608 testLength(4, map);
609
610 Expect.equals(0, map[eq01]);
611 Expect.equals(1, map[eq02]);
612 Expect.equals(2, map[eq11]);
613 Expect.equals(3, map[eq12]);
614
615 Expect.isTrue(map.containsKey(eq01));
616 Expect.isTrue(map.containsKey(eq02));
617 Expect.isTrue(map.containsKey(eq11));
618 Expect.isTrue(map.containsKey(eq12));
619
620 Expect.equals(1, map.remove(eq02));
621 Expect.equals(3, map.remove(eq12));
622 testLength(2, map);
623 Expect.isTrue(map.containsKey(eq01));
624 Expect.isFalse(map.containsKey(eq02));
625 Expect.isTrue(map.containsKey(eq11));
626 Expect.isFalse(map.containsKey(eq12));
627
628 Expect.equals(0, map[eq01]);
629 Expect.equals(null, map[eq02]);
630 Expect.equals(2, map[eq11]);
631 Expect.equals(null, map[eq12]);
632
633 Expect.equals(0, map.remove(eq01));
634 Expect.equals(2, map.remove(eq11));
635 testLength(0, map);
636
637 map[eq01] = 0;
638 map[eq02] = 1;
639 map[eq11] = 2;
640 map[eq12] = 3;
641 testLength(4, map);
642
643 // Transfer to equality-based map will collapse elements.
644 Map eqMap = new HashMap();
645 eqMap.addAll(map);
646 testLength(2, eqMap);
647 Expect.isTrue(eqMap.containsKey(eq01));
648 Expect.isTrue(eqMap.containsKey(eq02));
649 Expect.isTrue(eqMap.containsKey(eq11));
650 Expect.isTrue(eqMap.containsKey(eq12));
651
652 // Changing objects will not affect identity map.
653 map.clear();
654 var m1 = new Mutable(1);
655 var m2 = new Mutable(2);
656 var m3 = new Mutable(3);
657 map[m1] = 1;
658 map[m2] = 2;
659 map[m3] = 3;
660 Expect.equals(3, map.length);
661 Expect.isTrue(map.containsKey(m1));
662 Expect.isTrue(map.containsKey(m2));
663 Expect.isTrue(map.containsKey(m3));
664 Expect.notEquals(m1, m3);
665 m3.id = 1;
666 Expect.equals(m1, m3);
667 // Even if keys are equal, they are still not identical.
668 // Even if hashcode of m3 changed, it can still be found.
669 Expect.equals(1, map[m1]);
670 Expect.equals(3, map[m3]);
671 }
672
673 /** Class of objects that are equal if they hold the same id. */
674 class Equalizer {
675 int id;
676 Equalizer(this.id);
677 int get hashCode => id;
678 bool operator ==(Object other) =>
679 other is Equalizer && id == (other as Equalizer).id;
680 }
681
682 /**
683 * Objects that are not reflexive.
684 *
685 * They think they are better than their equals.
686 */
687 class Vampire {
688 final int generation;
689 const Vampire(this.generation);
690
691 int get hashCode => generation;
692
693 // The double-fang operator falsely claims that a vampire is equal to
694 // any of its sire's generation.
695 bool operator ==(Object other) =>
696 other is Vampire && generation - 1 == (other as Vampire).generation;
697 }
698
699 void testCustomMap(Map map) {
700 testLength(0, map);
701 var c11 = const Customer(1, 1);
702 var c12 = const Customer(1, 2);
703 var c21 = const Customer(2, 1);
704 var c22 = const Customer(2, 2);
705 // Sanity.
706 Expect.equals(c11, c12);
707 Expect.notEquals(c11, c21);
708 Expect.notEquals(c11, c22);
709 Expect.equals(c21, c22);
710 Expect.notEquals(c21, c11);
711 Expect.notEquals(c21, c12);
712
713 Expect.isTrue(myEquals(c11, c21));
714 Expect.isFalse(myEquals(c11, c12));
715 Expect.isFalse(myEquals(c11, c22));
716 Expect.isTrue(myEquals(c12, c22));
717 Expect.isFalse(myEquals(c12, c11));
718 Expect.isFalse(myEquals(c12, c21));
719
720 map[c11] = 42;
721 testLength(1, map);
722 Expect.isTrue(map.containsKey(c11));
723 Expect.isTrue(map.containsKey(c21));
724 Expect.isFalse(map.containsKey(c12));
725 Expect.isFalse(map.containsKey(c22));
726 Expect.equals(42, map[c11]);
727 Expect.equals(42, map[c21]);
728
729 map[c21] = 37;
730 testLength(1, map);
731 Expect.isTrue(map.containsKey(c11));
732 Expect.isTrue(map.containsKey(c21));
733 Expect.isFalse(map.containsKey(c12));
734 Expect.isFalse(map.containsKey(c22));
735 Expect.equals(37, map[c11]);
736 Expect.equals(37, map[c21]);
737
738 map[c22] = 42;
739 testLength(2, map);
740 Expect.isTrue(map.containsKey(c11));
741 Expect.isTrue(map.containsKey(c21));
742 Expect.isTrue(map.containsKey(c12));
743 Expect.isTrue(map.containsKey(c22));
744 Expect.equals(37, map[c11]);
745 Expect.equals(37, map[c21]);
746 Expect.equals(42, map[c12]);
747 Expect.equals(42, map[c22]);
748
749 Expect.equals(42, map.remove(c12));
750 testLength(1, map);
751 Expect.isTrue(map.containsKey(c11));
752 Expect.isTrue(map.containsKey(c21));
753 Expect.isFalse(map.containsKey(c12));
754 Expect.isFalse(map.containsKey(c22));
755 Expect.equals(37, map[c11]);
756 Expect.equals(37, map[c21]);
757
758 Expect.equals(37, map.remove(c11));
759 testLength(0, map);
760 }
761
762 void testUnmodifiableMap(Map map) {
763 Expect.isTrue(map.containsKey(1));
764 testLength(1, map);
765 Expect.equals(1, map.keys.first);
766 Expect.equals(37, map.values.first);
767
768 Expect.throws(map.clear);
769 Expect.throws(() {
770 map.remove(1);
771 });
772 Expect.throws(() {
773 map[2] = 42;
774 });
775 Expect.throws(() {
776 map.addAll({2: 42});
777 });
778 }
779
780 class Customer {
781 final int id;
782 final int secondId;
783 const Customer(this.id, this.secondId);
784 int get hashCode => id;
785 bool operator ==(Object other) {
786 if (other is! Customer) return false;
787 Customer otherCustomer = other;
788 return id == otherCustomer.id;
789 }
790 }
791
792 int myHashCode(Customer c) => c.secondId;
793 bool myEquals(Customer a, Customer b) => a.secondId == b.secondId;
794
795 void testIterationOrder(Map map) {
796 var order = [0, 6, 4, 2, 7, 9, 7, 1, 2, 5, 3];
797 for (int i = 0; i < order.length; i++) map[order[i]] = i;
798 Expect.listEquals(map.keys.toList(), [0, 6, 4, 2, 7, 9, 1, 5, 3]);
799 Expect.listEquals(map.values.toList(), [0, 1, 2, 8, 6, 5, 7, 9, 10]);
800 }
801
802 void testOtherKeys(Map<int, int> map) {
803 // Test that non-int keys are allowed in containsKey/remove/lookup.
804 // Custom hash sets and tree sets must be constructed so they don't
805 // use the equality/comparator on incompatible objects.
806
807 // This should not throw in either checked or unchecked mode.
808 map[0] = 0;
809 map[1] = 1;
810 map[2] = 2;
811 Expect.isFalse(map.containsKey("not an int"));
812 Expect.isFalse(map.containsKey(1.5));
813 Expect.isNull(map.remove("not an int"));
814 Expect.isNull(map.remove(1.5));
815 Expect.isNull(map["not an int"]);
816 Expect.isNull(map[1.5]);
817 }
818
819 class Mutable {
820 int id;
821 Mutable(this.id);
822 int get hashCode => id;
823 bool operator ==(other) => other is Mutable && other.id == id;
824 }
825
826 // Slow implementation of Map based on MapBase.
827 abstract class MapBaseOperations<K, V> {
828 final List _keys = <K>[];
829 final List _values = <V>[];
830 int _modCount = 0;
831
832 V operator [](Object key) {
833 int index = _keys.indexOf(key);
834 if (index < 0) return null;
835 return _values[index];
836 }
837
838 Iterable<K> get keys => new TestKeyIterable<K>(this);
839
840 void operator []=(K key, V value) {
841 int index = _keys.indexOf(key);
842 if (index >= 0) {
843 _values[index] = value;
844 } else {
845 _modCount++;
846 _keys.add(key);
847 _values.add(value);
848 }
849 }
850
851 V remove(Object key) {
852 int index = _keys.indexOf(key);
853 if (index >= 0) {
854 var result = _values[index];
855 key = _keys.removeLast();
856 var value = _values.removeLast();
857 if (index != _keys.length) {
858 _keys[index] = key;
859 _values[index] = value;
860 }
861 _modCount++;
862 return result;
863 }
864 return null;
865 }
866
867 void clear() {
868 // Clear cannot be based on remove, since remove won't remove keys that
869 // are not equal to themselves. It will fail the testNaNKeys test.
870 _keys.clear();
871 _values.clear();
872 _modCount++;
873 }
874 }
875
876 class MapBaseMap<K, V> = MapBase<K, V> with MapBaseOperations<K, V>;
877 class MapMixinMap<K, V> = MapBaseOperations<K, V> with MapMixin<K, V>;
878
879 class TestKeyIterable<K> extends IterableBase<K> {
880 final _map;
881 TestKeyIterable(this._map);
882 int get length => _map._keys.length;
883 Iterator<K> get iterator => new TestKeyIterator<K>(_map);
884 }
885
886 class TestKeyIterator<K> implements Iterator<K> {
887 final _map;
888 final int _modCount;
889 int _index = 0;
890 var _current;
891 TestKeyIterator(map)
892 : _map = map,
893 _modCount = map._modCount;
894 bool moveNext() {
895 if (_modCount != _map._modCount) {
896 throw new ConcurrentModificationError(_map);
897 }
898 if (_index == _map._keys.length) {
899 _current = null;
900 return false;
901 }
902 _current = _map._keys[_index++];
903 return true;
904 }
905
906 K get current => _current;
907 }
908
909 // Slow implementation of Map based on MapBase.
910 class UnmodifiableMapBaseMap<K, V> extends UnmodifiableMapBase<K, V> {
911 final List _keys = <K>[];
912 final List _values = <V>[];
913 UnmodifiableMapBaseMap(List pairs) {
914 for (int i = 0; i < pairs.length; i += 2) {
915 _keys.add(pairs[i]);
916 _values.add(pairs[i + 1]);
917 }
918 }
919
920 int get _modCount => 0;
921
922 V operator [](K key) {
923 int index = _keys.indexOf(key);
924 if (index < 0) return null;
925 return _values[index];
926 }
927
928 Iterable<K> get keys => _keys.skip(0);
929 }
930
931 abstract class Super implements Comparable {}
932
933 abstract class Interface implements Comparable {}
934
935 class Sub extends Super implements Interface, Comparable {
936 int compareTo(Sub other) => 0;
937 int get hashCode => 0;
938 bool operator ==(other) => other is Sub;
939 }
940
941 expectMap(Map expect, Map actual) {
942 Expect.equals(expect.length, actual.length, "length");
943 for (var key in expect.keys) {
944 Expect.isTrue(actual.containsKey(key), "containsKey $key");
945 Expect.equals(expect[key], actual[key]);
946 }
947 }
948
949 void testFrom() {
950 // Check contents.
951 for (var map in [
952 {},
953 {1: 1},
954 {1: 2, 3: 4, 5: 6, 7: 8}
955 ]) {
956 expectMap(map, new Map.from(map));
957 expectMap(map, new HashMap.from(map));
958 expectMap(map, new LinkedHashMap.from(map));
959 expectMap(map, new SplayTreeMap.from(map));
960 }
961 // Test type combinations allowed.
962 Map<int, int> intMap = <int, int>{1: 2, 3: 4};
963 Map<num, num> numMap = <num, num>{1: 2, 3: 4};
964 expectMap(intMap, new Map<int, int>.from(numMap));
965 expectMap(intMap, new Map<num, num>.from(intMap));
966 expectMap(intMap, new HashMap<int, int>.from(numMap));
967 expectMap(intMap, new HashMap<num, num>.from(intMap));
968 expectMap(intMap, new LinkedHashMap<int, int>.from(numMap));
969 expectMap(intMap, new LinkedHashMap<num, num>.from(intMap));
970 expectMap(intMap, new SplayTreeMap<int, int>.from(numMap));
971 expectMap(intMap, new SplayTreeMap<num, num>.from(intMap));
972
973 var sub = new Sub();
974 Map<Super, Super> superMap = <Super, Super>{sub: sub};
975 Map<Interface, Interface> interfaceMap = <Interface, Interface>{sub: sub};
976 expectMap(superMap, new Map<Super, Super>.from(interfaceMap));
977 expectMap(superMap, new Map<Interface, Interface>.from(superMap));
978 expectMap(superMap, new HashMap<Super, Super>.from(interfaceMap));
979 expectMap(superMap, new HashMap<Interface, Interface>.from(superMap));
980 expectMap(superMap, new LinkedHashMap<Super, Super>.from(interfaceMap));
981 expectMap(superMap, new LinkedHashMap<Interface, Interface>.from(superMap));
982 expectMap(superMap, new SplayTreeMap<Super, Super>.from(interfaceMap));
983 expectMap(superMap, new SplayTreeMap<Interface, Interface>.from(superMap));
984 }
OLDNEW
« no previous file with comments | « tests/corelib_strong/map_remove_test.dart ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698