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 // Patch file for dart:collection classes. | 5 // Patch file for dart:collection classes. |
6 import 'dart:_foreign_helper' show JS; | 6 import 'dart:_foreign_helper' show JS; |
7 import 'dart:_js_helper' show | 7 import 'dart:_js_helper' show |
8 fillLiteralMap, InternalMap, NoInline, NoThrows, patch, JsLinkedHashMap, | 8 fillLiteralMap, InternalMap, NoInline, NoThrows, patch, JsLinkedHashMap, |
9 LinkedHashMapCell, LinkedHashMapKeyIterable, LinkedHashMapKeyIterator; | 9 LinkedHashMapCell, LinkedHashMapKeyIterable, LinkedHashMapKeyIterator; |
10 | 10 |
(...skipping 368 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
379 if (identical(JS('var', '#[#]', bucket, i), key)) return i; | 379 if (identical(JS('var', '#[#]', bucket, i), key)) return i; |
380 } | 380 } |
381 return -1; | 381 return -1; |
382 } | 382 } |
383 } | 383 } |
384 | 384 |
385 class _CustomHashMap<K, V> extends _HashMap<K, V> { | 385 class _CustomHashMap<K, V> extends _HashMap<K, V> { |
386 final _Equality<K> _equals; | 386 final _Equality<K> _equals; |
387 final _Hasher<K> _hashCode; | 387 final _Hasher<K> _hashCode; |
388 final _Predicate _validKey; | 388 final _Predicate _validKey; |
389 | |
390 _CustomHashMap(this._equals, this._hashCode, bool validKey(potentialKey)) | 389 _CustomHashMap(this._equals, this._hashCode, bool validKey(potentialKey)) |
391 : _validKey = (validKey != null) ? validKey : ((v) => v is K); | 390 : _validKey = (validKey != null) ? validKey : ((v) => v is K); |
392 | 391 |
393 V operator[](Object key) { | 392 V operator[](Object key) { |
394 if (!_validKey(key)) return null; | 393 if (!_validKey(key)) return null; |
395 return super._get(key); | 394 return super._get(key); |
396 } | 395 } |
397 | 396 |
398 void operator[]=(K key, V value) { | 397 void operator[]=(K key, V value) { |
399 super._set(key, value); | 398 super._set(key, value); |
(...skipping 86 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
486 | 485 |
487 @patch | 486 @patch |
488 class LinkedHashMap<K, V> { | 487 class LinkedHashMap<K, V> { |
489 @patch | 488 @patch |
490 factory LinkedHashMap({ bool equals(K key1, K key2), | 489 factory LinkedHashMap({ bool equals(K key1, K key2), |
491 int hashCode(K key), | 490 int hashCode(K key), |
492 bool isValidKey(potentialKey) }) { | 491 bool isValidKey(potentialKey) }) { |
493 if (isValidKey == null) { | 492 if (isValidKey == null) { |
494 if (hashCode == null) { | 493 if (hashCode == null) { |
495 if (equals == null) { | 494 if (equals == null) { |
496 return new JsLinkedHashMap<K, V>.es6(); | 495 return new JsLinkedHashMap<K, V>(); |
497 } | 496 } |
498 hashCode = _defaultHashCode; | 497 hashCode = _defaultHashCode; |
499 } else { | 498 } else { |
500 if (identical(identityHashCode, hashCode) && | 499 if (identical(identityHashCode, hashCode) && |
501 identical(identical, equals)) { | 500 identical(identical, equals)) { |
502 return new _LinkedIdentityHashMap<K, V>(); | 501 return new _LinkedIdentityHashMap<K, V>(); |
503 } | 502 } |
504 if (equals == null) { | 503 if (equals == null) { |
505 equals = _defaultEquals; | 504 equals = _defaultEquals; |
506 } | 505 } |
507 } | 506 } |
508 } else { | 507 } else { |
509 if (hashCode == null) { | 508 if (hashCode == null) { |
510 hashCode = _defaultHashCode; | 509 hashCode = _defaultHashCode; |
511 } | 510 } |
512 if (equals == null) { | 511 if (equals == null) { |
513 equals = _defaultEquals; | 512 equals = _defaultEquals; |
514 } | 513 } |
515 } | 514 } |
516 return new _LinkedCustomHashMap<K, V>(equals, hashCode, isValidKey); | 515 return new _LinkedCustomHashMap<K, V>(equals, hashCode, isValidKey); |
517 } | 516 } |
518 | 517 |
519 @patch | 518 @patch |
520 factory LinkedHashMap.identity() = _LinkedIdentityHashMap<K, V>; | 519 factory LinkedHashMap.identity() = _LinkedIdentityHashMap<K, V>; |
521 | 520 |
522 // Private factory constructor called by generated code for map literals. | 521 // Private factory constructor called by generated code for map literals. |
523 @NoInline() | 522 @NoInline() |
524 factory LinkedHashMap._literal(List keyValuePairs) { | 523 factory LinkedHashMap._literal(List keyValuePairs) { |
525 return fillLiteralMap(keyValuePairs, new JsLinkedHashMap<K, V>.es6()); | 524 return fillLiteralMap(keyValuePairs, new JsLinkedHashMap<K, V>()); |
526 } | 525 } |
527 | 526 |
528 // Private factory constructor called by generated code for map literals. | 527 // Private factory constructor called by generated code for map literals. |
529 @NoThrows() @NoInline() | 528 @NoThrows() @NoInline() |
530 factory LinkedHashMap._empty() { | 529 factory LinkedHashMap._empty() { |
531 return new JsLinkedHashMap<K, V>.es6(); | 530 return new JsLinkedHashMap<K, V>(); |
532 } | 531 } |
533 } | 532 } |
534 | 533 |
535 // TODO(floitsch): use ES6 Maps when available. | |
536 class _LinkedIdentityHashMap<K, V> extends JsLinkedHashMap<K, V> { | 534 class _LinkedIdentityHashMap<K, V> extends JsLinkedHashMap<K, V> { |
537 int internalComputeHashCode(var key) { | 535 int internalComputeHashCode(var key) { |
538 // We force the hash codes to be unsigned 30-bit integers to avoid | 536 // We force the hash codes to be unsigned 30-bit integers to avoid |
539 // issues with problematic keys like '__proto__'. Another option | 537 // issues with problematic keys like '__proto__'. Another option |
540 // would be to throw an exception if the hash code isn't a number. | 538 // would be to throw an exception if the hash code isn't a number. |
541 return JS('int', '# & 0x3ffffff', identityHashCode(key)); | 539 return JS('int', '# & 0x3ffffff', identityHashCode(key)); |
542 } | 540 } |
543 | 541 |
544 int internalFindBucketIndex(var bucket, var key) { | 542 int internalFindBucketIndex(var bucket, var key) { |
545 if (bucket == null) return -1; | 543 if (bucket == null) return -1; |
546 int length = JS('int', '#.length', bucket); | 544 int length = JS('int', '#.length', bucket); |
547 for (int i = 0; i < length; i++) { | 545 for (int i = 0; i < length; i++) { |
548 LinkedHashMapCell cell = JS('var', '#[#]', bucket, i); | 546 LinkedHashMapCell cell = JS('var', '#[#]', bucket, i); |
549 if (identical(cell.hashMapCellKey, key)) return i; | 547 if (identical(cell.hashMapCellKey, key)) return i; |
550 } | 548 } |
551 return -1; | 549 return -1; |
552 } | 550 } |
553 } | 551 } |
554 | 552 |
555 // TODO(floitsch): use ES6 maps when available. | |
556 class _LinkedCustomHashMap<K, V> extends JsLinkedHashMap<K, V> { | 553 class _LinkedCustomHashMap<K, V> extends JsLinkedHashMap<K, V> { |
557 final _Equality<K> _equals; | 554 final _Equality<K> _equals; |
558 final _Hasher<K> _hashCode; | 555 final _Hasher<K> _hashCode; |
559 final _Predicate _validKey; | 556 final _Predicate _validKey; |
560 | |
561 _LinkedCustomHashMap(this._equals, this._hashCode, | 557 _LinkedCustomHashMap(this._equals, this._hashCode, |
562 bool validKey(potentialKey)) | 558 bool validKey(potentialKey)) |
563 : _validKey = (validKey != null) ? validKey : ((v) => v is K); | 559 : _validKey = (validKey != null) ? validKey : ((v) => v is K); |
564 | 560 |
565 V operator[](Object key) { | 561 V operator[](Object key) { |
566 if (!_validKey(key)) return null; | 562 if (!_validKey(key)) return null; |
567 return super.internalGet(key); | 563 return super.internalGet(key); |
568 } | 564 } |
569 | 565 |
570 void operator[]=(K key, V value) { | 566 void operator[]=(K key, V value) { |
(...skipping 891 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1462 } else if (_cell == null) { | 1458 } else if (_cell == null) { |
1463 _current = null; | 1459 _current = null; |
1464 return false; | 1460 return false; |
1465 } else { | 1461 } else { |
1466 _current = _cell._element; | 1462 _current = _cell._element; |
1467 _cell = _cell._next; | 1463 _cell = _cell._next; |
1468 return true; | 1464 return true; |
1469 } | 1465 } |
1470 } | 1466 } |
1471 } | 1467 } |
OLD | NEW |