export class UniversalWeakMap { constructor() {
A map data structure that holds object keys weakly, yet can also hold non-object keys, unlike the native WeakMap
.
export class UniversalWeakMap { constructor() {
Since a WeakMap
cannot hold primitive values as keys, we need a backup Map
instance to hold primitive keys. Both this._weakMap
and this._strongMap
are lazily initialized.
this._weakMap = null; this._strongMap = null; }
Since get
and set
are the only methods used, that’s all I’ve implemented here.
get(key) { const map = this._getMap(key, false); if (map) { return map.get(key); } } set(key, value) { this._getMap(key, true).set(key, value);
An actual Map
or WeakMap
would return this
here, but returning the value
is more convenient for the tuple
implementation.
return value; } _getMap(key, canCreate) { if (! canCreate) { return isObjRef(key) ? this._weakMap : this._strongMap; } if (isObjRef(key)) { return this._weakMap || (this._weakMap = new WeakMap); } return this._strongMap || (this._strongMap = new Map); } } function isObjRef(value) { switch (typeof value) { case "object": if (value === null) { return false; } case "function": return true; default: return false; } }