1 | 'use strict';
|
2 | var uncurryThis = require('../internals/function-uncurry-this');
|
3 | var defineBuiltIns = require('../internals/define-built-ins');
|
4 | var getWeakData = require('../internals/internal-metadata').getWeakData;
|
5 | var anInstance = require('../internals/an-instance');
|
6 | var anObject = require('../internals/an-object');
|
7 | var isNullOrUndefined = require('../internals/is-null-or-undefined');
|
8 | var isObject = require('../internals/is-object');
|
9 | var iterate = require('../internals/iterate');
|
10 | var ArrayIterationModule = require('../internals/array-iteration');
|
11 | var hasOwn = require('../internals/has-own-property');
|
12 | var InternalStateModule = require('../internals/internal-state');
|
13 |
|
14 | var setInternalState = InternalStateModule.set;
|
15 | var internalStateGetterFor = InternalStateModule.getterFor;
|
16 | var find = ArrayIterationModule.find;
|
17 | var findIndex = ArrayIterationModule.findIndex;
|
18 | var splice = uncurryThis([].splice);
|
19 | var id = 0;
|
20 |
|
21 |
|
22 | var uncaughtFrozenStore = function (state) {
|
23 | return state.frozen || (state.frozen = new UncaughtFrozenStore());
|
24 | };
|
25 |
|
26 | var UncaughtFrozenStore = function () {
|
27 | this.entries = [];
|
28 | };
|
29 |
|
30 | var findUncaughtFrozen = function (store, key) {
|
31 | return find(store.entries, function (it) {
|
32 | return it[0] === key;
|
33 | });
|
34 | };
|
35 |
|
36 | UncaughtFrozenStore.prototype = {
|
37 | get: function (key) {
|
38 | var entry = findUncaughtFrozen(this, key);
|
39 | if (entry) return entry[1];
|
40 | },
|
41 | has: function (key) {
|
42 | return !!findUncaughtFrozen(this, key);
|
43 | },
|
44 | set: function (key, value) {
|
45 | var entry = findUncaughtFrozen(this, key);
|
46 | if (entry) entry[1] = value;
|
47 | else this.entries.push([key, value]);
|
48 | },
|
49 | 'delete': function (key) {
|
50 | var index = findIndex(this.entries, function (it) {
|
51 | return it[0] === key;
|
52 | });
|
53 | if (~index) splice(this.entries, index, 1);
|
54 | return !!~index;
|
55 | }
|
56 | };
|
57 |
|
58 | module.exports = {
|
59 | getConstructor: function (wrapper, CONSTRUCTOR_NAME, IS_MAP, ADDER) {
|
60 | var Constructor = wrapper(function (that, iterable) {
|
61 | anInstance(that, Prototype);
|
62 | setInternalState(that, {
|
63 | type: CONSTRUCTOR_NAME,
|
64 | id: id++,
|
65 | frozen: undefined
|
66 | });
|
67 | if (!isNullOrUndefined(iterable)) iterate(iterable, that[ADDER], { that: that, AS_ENTRIES: IS_MAP });
|
68 | });
|
69 |
|
70 | var Prototype = Constructor.prototype;
|
71 |
|
72 | var getInternalState = internalStateGetterFor(CONSTRUCTOR_NAME);
|
73 |
|
74 | var define = function (that, key, value) {
|
75 | var state = getInternalState(that);
|
76 | var data = getWeakData(anObject(key), true);
|
77 | if (data === true) uncaughtFrozenStore(state).set(key, value);
|
78 | else data[state.id] = value;
|
79 | return that;
|
80 | };
|
81 |
|
82 | defineBuiltIns(Prototype, {
|
83 |
|
84 |
|
85 |
|
86 | 'delete': function (key) {
|
87 | var state = getInternalState(this);
|
88 | if (!isObject(key)) return false;
|
89 | var data = getWeakData(key);
|
90 | if (data === true) return uncaughtFrozenStore(state)['delete'](key);
|
91 | return data && hasOwn(data, state.id) && delete data[state.id];
|
92 | },
|
93 |
|
94 |
|
95 |
|
96 | has: function has(key) {
|
97 | var state = getInternalState(this);
|
98 | if (!isObject(key)) return false;
|
99 | var data = getWeakData(key);
|
100 | if (data === true) return uncaughtFrozenStore(state).has(key);
|
101 | return data && hasOwn(data, state.id);
|
102 | }
|
103 | });
|
104 |
|
105 | defineBuiltIns(Prototype, IS_MAP ? {
|
106 |
|
107 |
|
108 | get: function get(key) {
|
109 | var state = getInternalState(this);
|
110 | if (isObject(key)) {
|
111 | var data = getWeakData(key);
|
112 | if (data === true) return uncaughtFrozenStore(state).get(key);
|
113 | return data ? data[state.id] : undefined;
|
114 | }
|
115 | },
|
116 |
|
117 |
|
118 | set: function set(key, value) {
|
119 | return define(this, key, value);
|
120 | }
|
121 | } : {
|
122 |
|
123 |
|
124 | add: function add(value) {
|
125 | return define(this, value, true);
|
126 | }
|
127 | });
|
128 |
|
129 | return Constructor;
|
130 | }
|
131 | };
|