Chromium Code Reviews| Index: sdk/lib/_internal/lib/constant_map.dart |
| diff --git a/sdk/lib/_internal/lib/constant_map.dart b/sdk/lib/_internal/lib/constant_map.dart |
| index 60300fc39e4d42105da7097350cc7255be4c1399..2b5d1e6cf7557835124cb8b9fa465be94fe454cb 100644 |
| --- a/sdk/lib/_internal/lib/constant_map.dart |
| +++ b/sdk/lib/_internal/lib/constant_map.dart |
| @@ -4,75 +4,119 @@ |
| part of _js_helper; |
| +abstract class ConstantMap<K, V> implements Map<K, V> { |
| + bool get isEmpty => length == 0; |
| + |
| + bool get isNotEmpty => !isEmpty; |
| + |
| + String toString() => Maps.mapToString(this); |
| + |
| + _throwUnmodifiable() { |
| + throw new UnsupportedError("Cannot modify unmodifiable Map"); |
| + } |
| + void operator []=(K key, V val) => _throwUnmodifiable(); |
| + V putIfAbsent(K key, V ifAbsent()) => _throwUnmodifiable(); |
| + V remove(K key) => _throwUnmodifiable(); |
| + void clear() => _throwUnmodifiable(); |
| + void addAll(Map<K, V> other) => _throwUnmodifiable(); |
| +} |
| + |
| // This class has no constructor. This is on purpose since the instantiation |
| // is shortcut by the compiler. |
| -class ConstantMap<V> implements Map<String, V> { |
| +class ConstantStringMap<K, V> extends ConstantMap<K, V> { |
| final int length; |
| // A constant map is backed by a JavaScript object. |
| final _jsObject; |
| - final List<String> _keys; |
| + final List<K> _keys; |
| bool containsValue(V needle) { |
| return values.any((V value) => value == needle); |
| } |
| - bool containsKey(String key) { |
| + bool containsKey(Object key) { |
| + if (key is! String) return false; |
| if (key == '__proto__') return false; |
| return jsHasOwnProperty(_jsObject, key); |
| } |
| - V operator [](String key) { |
| + V operator [](Object key) { |
| + if (key is! String) return null; |
| if (!containsKey(key)) return null; |
| return jsPropertyAccess(_jsObject, key); |
| } |
| - void forEach(void f(String key, V value)) { |
| - _keys.forEach((String key) => f(key, this[key])); |
| + void forEach(void f(K key, V value)) { |
| + _keys.forEach((key) => f(key, this[key])); |
| } |
| - Iterable<String> get keys { |
| - return new _ConstantMapKeyIterable(this); |
| + Iterable<K> get keys { |
| + return new _ConstantMapKeyIterable<K>(this); |
| } |
| Iterable<V> get values { |
| - return _keys.map((String key) => this[key]); |
| - } |
| - |
| - bool get isEmpty => length == 0; |
| - |
| - bool get isNotEmpty => !isEmpty; |
| - |
| - String toString() => Maps.mapToString(this); |
| - |
| - _throwUnmodifiable() { |
| - throw new UnsupportedError("Cannot modify unmodifiable Map"); |
| + return _keys.map((key) => this[key]); |
| } |
| - void operator []=(String key, V val) => _throwUnmodifiable(); |
| - V putIfAbsent(String key, V ifAbsent()) => _throwUnmodifiable(); |
| - V remove(String key) => _throwUnmodifiable(); |
| - void clear() => _throwUnmodifiable(); |
| - void addAll(Map<String, V> other) => _throwUnmodifiable(); |
| } |
| // This class has no constructor. This is on purpose since the instantiation |
| // is shortcut by the compiler. |
| -class ConstantProtoMap<V> extends ConstantMap<V> { |
| +class ConstantProtoMap<K, V> extends ConstantStringMap<K, V> { |
| final V _protoValue; |
| - bool containsKey(String key) { |
| + bool containsKey(K key) { |
|
ngeoffray
2013/09/18 14:32:08
Object
Johnni Winther
2013/09/18 14:53:47
Done.
|
| if (key == '__proto__') return true; |
| return super.containsKey(key); |
| } |
| - V operator [](String key) { |
| + V operator [](K key) { |
|
ngeoffray
2013/09/18 14:32:08
Object
Johnni Winther
2013/09/18 14:53:47
Done.
|
| if (key == '__proto__') return _protoValue; |
| return super[key]; |
| } |
| } |
| -class _ConstantMapKeyIterable extends IterableBase<String> { |
| - ConstantMap _map; |
| +class _ConstantMapKeyIterable<K> extends IterableBase<K> { |
| + ConstantStringMap<K, dynamic> _map; |
| _ConstantMapKeyIterable(this._map); |
| - Iterator<String> get iterator => _map._keys.iterator; |
| + Iterator<K> get iterator => _map._keys.iterator; |
| +} |
| + |
| +// This class has no constructor. This is on purpose since the instantiation |
| +// is shortcut by the compiler. |
| +class GeneralConstantMap<K, V> extends ConstantMap<K, V> { |
| + // [_jsData] holds a key-value pair list. |
| + final _jsData; |
| + |
| + // We cannot create the backing map on creation since hashCode interceptors |
| + // have not been defined when constants are created. |
| + Map<K, V> _getMap() { |
| + if (JS('bool', r'!this.$map')) { |
| + JS('', r'this.$map = #', makeConstantMap(_jsData)); |
| + } |
| + return JS('Map', r'this.$map'); |
| + } |
| + |
| + bool containsValue(V needle) { |
| + return _getMap().containsValue(needle); |
| + } |
| + |
| + bool containsKey(Object key) { |
| + return _getMap().containsKey(key); |
| + } |
| + |
| + V operator [](Object key) { |
| + return _getMap()[key]; |
| + } |
| + |
| + void forEach(void f(K key, V value)) { |
| + _getMap().forEach(f); |
| + } |
| + |
| + Iterable<K> get keys { |
| + return _getMap().keys; |
| + } |
| + |
| + Iterable<V> get values { |
| + return _getMap().values; |
| + } |
| } |