Spaces:
Runtime error
Runtime error
| ; | |
| var dP = require('./_object-dp').f; | |
| var create = require('./_object-create'); | |
| var redefineAll = require('./_redefine-all'); | |
| var ctx = require('./_ctx'); | |
| var anInstance = require('./_an-instance'); | |
| var forOf = require('./_for-of'); | |
| var $iterDefine = require('./_iter-define'); | |
| var step = require('./_iter-step'); | |
| var setSpecies = require('./_set-species'); | |
| var DESCRIPTORS = require('./_descriptors'); | |
| var fastKey = require('./_meta').fastKey; | |
| var validate = require('./_validate-collection'); | |
| var SIZE = DESCRIPTORS ? '_s' : 'size'; | |
| var getEntry = function (that, key) { | |
| // fast case | |
| var index = fastKey(key); | |
| var entry; | |
| if (index !== 'F') return that._i[index]; | |
| // frozen object case | |
| for (entry = that._f; entry; entry = entry.n) { | |
| if (entry.k == key) return entry; | |
| } | |
| }; | |
| module.exports = { | |
| getConstructor: function (wrapper, NAME, IS_MAP, ADDER) { | |
| var C = wrapper(function (that, iterable) { | |
| anInstance(that, C, NAME, '_i'); | |
| that._t = NAME; // collection type | |
| that._i = create(null); // index | |
| that._f = undefined; // first entry | |
| that._l = undefined; // last entry | |
| that[SIZE] = 0; // size | |
| if (iterable != undefined) forOf(iterable, IS_MAP, that[ADDER], that); | |
| }); | |
| redefineAll(C.prototype, { | |
| // 23.1.3.1 Map.prototype.clear() | |
| // 23.2.3.2 Set.prototype.clear() | |
| clear: function clear() { | |
| for (var that = validate(this, NAME), data = that._i, entry = that._f; entry; entry = entry.n) { | |
| entry.r = true; | |
| if (entry.p) entry.p = entry.p.n = undefined; | |
| delete data[entry.i]; | |
| } | |
| that._f = that._l = undefined; | |
| that[SIZE] = 0; | |
| }, | |
| // 23.1.3.3 Map.prototype.delete(key) | |
| // 23.2.3.4 Set.prototype.delete(value) | |
| 'delete': function (key) { | |
| var that = validate(this, NAME); | |
| var entry = getEntry(that, key); | |
| if (entry) { | |
| var next = entry.n; | |
| var prev = entry.p; | |
| delete that._i[entry.i]; | |
| entry.r = true; | |
| if (prev) prev.n = next; | |
| if (next) next.p = prev; | |
| if (that._f == entry) that._f = next; | |
| if (that._l == entry) that._l = prev; | |
| that[SIZE]--; | |
| } return !!entry; | |
| }, | |
| // 23.2.3.6 Set.prototype.forEach(callbackfn, thisArg = undefined) | |
| // 23.1.3.5 Map.prototype.forEach(callbackfn, thisArg = undefined) | |
| forEach: function forEach(callbackfn /* , that = undefined */) { | |
| validate(this, NAME); | |
| var f = ctx(callbackfn, arguments.length > 1 ? arguments[1] : undefined, 3); | |
| var entry; | |
| while (entry = entry ? entry.n : this._f) { | |
| f(entry.v, entry.k, this); | |
| // revert to the last existing entry | |
| while (entry && entry.r) entry = entry.p; | |
| } | |
| }, | |
| // 23.1.3.7 Map.prototype.has(key) | |
| // 23.2.3.7 Set.prototype.has(value) | |
| has: function has(key) { | |
| return !!getEntry(validate(this, NAME), key); | |
| } | |
| }); | |
| if (DESCRIPTORS) dP(C.prototype, 'size', { | |
| get: function () { | |
| return validate(this, NAME)[SIZE]; | |
| } | |
| }); | |
| return C; | |
| }, | |
| def: function (that, key, value) { | |
| var entry = getEntry(that, key); | |
| var prev, index; | |
| // change existing entry | |
| if (entry) { | |
| entry.v = value; | |
| // create new entry | |
| } else { | |
| that._l = entry = { | |
| i: index = fastKey(key, true), // <- index | |
| k: key, // <- key | |
| v: value, // <- value | |
| p: prev = that._l, // <- previous entry | |
| n: undefined, // <- next entry | |
| r: false // <- removed | |
| }; | |
| if (!that._f) that._f = entry; | |
| if (prev) prev.n = entry; | |
| that[SIZE]++; | |
| // add to index | |
| if (index !== 'F') that._i[index] = entry; | |
| } return that; | |
| }, | |
| getEntry: getEntry, | |
| setStrong: function (C, NAME, IS_MAP) { | |
| // add .keys, .values, .entries, [@@iterator] | |
| // 23.1.3.4, 23.1.3.8, 23.1.3.11, 23.1.3.12, 23.2.3.5, 23.2.3.8, 23.2.3.10, 23.2.3.11 | |
| $iterDefine(C, NAME, function (iterated, kind) { | |
| this._t = validate(iterated, NAME); // target | |
| this._k = kind; // kind | |
| this._l = undefined; // previous | |
| }, function () { | |
| var that = this; | |
| var kind = that._k; | |
| var entry = that._l; | |
| // revert to the last existing entry | |
| while (entry && entry.r) entry = entry.p; | |
| // get next entry | |
| if (!that._t || !(that._l = entry = entry ? entry.n : that._t._f)) { | |
| // or finish the iteration | |
| that._t = undefined; | |
| return step(1); | |
| } | |
| // return step by kind | |
| if (kind == 'keys') return step(0, entry.k); | |
| if (kind == 'values') return step(0, entry.v); | |
| return step(0, [entry.k, entry.v]); | |
| }, IS_MAP ? 'entries' : 'values', !IS_MAP, true); | |
| // add [@@species], 23.1.2.2, 23.2.2.2 | |
| setSpecies(NAME); | |
| } | |
| }; | |