@jiovan-labs/ts-multi-map 0.0.0-stage → 2.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (36) hide show
  1. package/LICENSE.txt +21 -0
  2. package/README.md +46 -2
  3. package/dist/cjs/index.d.ts +7 -0
  4. package/dist/cjs/index.js +47 -0
  5. package/dist/cjs/type/declaration.d.ts +10 -0
  6. package/dist/cjs/type/declaration.js +17 -0
  7. package/dist/cjs/util/MultiKeyMap.d.ts +34 -0
  8. package/dist/cjs/util/MultiKeyMap.js +530 -0
  9. package/dist/cjs/util/MultiValueMap.d.ts +35 -0
  10. package/dist/cjs/util/MultiValueMap.js +527 -0
  11. package/dist/cjs/util/RangeMap.d.ts +36 -0
  12. package/dist/cjs/util/RangeMap.js +584 -0
  13. package/dist/cjs/util/ReadonlyMultiKeyMap.d.ts +27 -0
  14. package/dist/cjs/util/ReadonlyMultiKeyMap.js +364 -0
  15. package/dist/cjs/util/ReadonlyMultiValueMap.d.ts +27 -0
  16. package/dist/cjs/util/ReadonlyMultiValueMap.js +365 -0
  17. package/dist/cjs/util/ReadonlyRangeMap.d.ts +27 -0
  18. package/dist/cjs/util/ReadonlyRangeMap.js +376 -0
  19. package/dist/esm/index.d.ts +7 -0
  20. package/dist/esm/index.js +7 -0
  21. package/dist/esm/type/declaration.d.ts +10 -0
  22. package/dist/esm/type/declaration.js +1 -0
  23. package/dist/esm/util/MultiKeyMap.d.ts +34 -0
  24. package/dist/esm/util/MultiKeyMap.js +318 -0
  25. package/dist/esm/util/MultiValueMap.d.ts +35 -0
  26. package/dist/esm/util/MultiValueMap.js +328 -0
  27. package/dist/esm/util/RangeMap.d.ts +36 -0
  28. package/dist/esm/util/RangeMap.js +358 -0
  29. package/dist/esm/util/ReadonlyMultiKeyMap.d.ts +27 -0
  30. package/dist/esm/util/ReadonlyMultiKeyMap.js +136 -0
  31. package/dist/esm/util/ReadonlyMultiValueMap.d.ts +27 -0
  32. package/dist/esm/util/ReadonlyMultiValueMap.js +136 -0
  33. package/dist/esm/util/ReadonlyRangeMap.d.ts +27 -0
  34. package/dist/esm/util/ReadonlyRangeMap.js +135 -0
  35. package/dist/umd/ts-multi-map.min.js +1 -0
  36. package/package.json +111 -5
@@ -0,0 +1,584 @@
1
+ var __create = Object.create;
2
+ var __defProp = Object.defineProperty;
3
+ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
4
+ var __getOwnPropNames = Object.getOwnPropertyNames;
5
+ var __getProtoOf = Object.getPrototypeOf;
6
+ var __hasOwnProp = Object.prototype.hasOwnProperty;
7
+ var __export = (target, all) => {
8
+ for (var name in all)
9
+ __defProp(target, name, { get: all[name], enumerable: true });
10
+ };
11
+ var __copyProps = (to, from, except, desc) => {
12
+ if (from && typeof from === "object" || typeof from === "function") {
13
+ for (let key of __getOwnPropNames(from))
14
+ if (!__hasOwnProp.call(to, key) && key !== except)
15
+ __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
16
+ }
17
+ return to;
18
+ };
19
+ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(
20
+ // If the importer is in node compatibility mode or this is not an ESM
21
+ // file that has been converted to a CommonJS file using a Babel-
22
+ // compatible transform (i.e. "__esModule" has not been set), then set
23
+ // "default" to the CommonJS "module.exports" for node compatibility.
24
+ isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", { value: mod, enumerable: true }) : target,
25
+ mod
26
+ ));
27
+ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
28
+
29
+ // src/util/RangeMap.ts
30
+ var RangeMap_exports = {};
31
+ __export(RangeMap_exports, {
32
+ RangeMap: () => RangeMap
33
+ });
34
+ module.exports = __toCommonJS(RangeMap_exports);
35
+ var import_object_hash = __toESM(require("object-hash"));
36
+ var RangeMap = class {
37
+ /**
38
+ * Construct a range map instance
39
+ *
40
+ * @param entries the map entries
41
+ * @param validation whether to compare the ranges to all the ranges previously, to determine if there are any conflicts
42
+ *
43
+ * @example
44
+ * ```ts
45
+ * const map = new RangeMap([
46
+ * [[1, 30], 'green'],
47
+ * [[30, 60], 'blue'],
48
+ * [[60, 90], 'orange'],
49
+ * [[90, 100, true, true], 'red']
50
+ * ]);
51
+ * ```
52
+ */
53
+ constructor(entries, validation = true) {
54
+ this.keyMap = /* @__PURE__ */ new Map();
55
+ this.valueMap = /* @__PURE__ */ new Map();
56
+ entries == null ? void 0 : entries.forEach((entry) => {
57
+ const [k, v] = entry;
58
+ this.set(k, v, validation);
59
+ });
60
+ }
61
+ /**
62
+ * Construct a range map instance
63
+ *
64
+ * @param entries the map entries
65
+ * @param validation whether to compare the ranges to all the ranges previously, to determine if there are any conflicts
66
+ *
67
+ * @returns a range map instance
68
+ *
69
+ * @example
70
+ * ```ts
71
+ * const map = RangeMap.of([
72
+ * [[1, 30], 'green'],
73
+ * [[30, 60], 'blue'],
74
+ * [[60, 90], 'orange'],
75
+ * [[90, 100, true, true], 'red']
76
+ * ]);
77
+ * ```
78
+ */
79
+ static of(entries, validation = true) {
80
+ return new RangeMap(entries, validation);
81
+ }
82
+ /**
83
+ * Returns the value of the given key
84
+ *
85
+ * @param key the key to retrieve
86
+ * @param defaults the default value if not found
87
+ *
88
+ * @returns the value of the given key
89
+ *
90
+ * @example
91
+ * ```ts
92
+ * const map = RangeMap.of([
93
+ * [[1, 50, true, true], 'white'],
94
+ * [[51, 100, false, true], 'black']
95
+ * ]);
96
+ * map.get([1, 50, true, true]); // 'white'
97
+ * map.get([51, 100, false, true]); // 'black'
98
+ * ```
99
+ */
100
+ get(key, defaults) {
101
+ const hash = (0, import_object_hash.default)(this.toInternalKey(key));
102
+ return this.valueMap.get(hash) ?? defaults;
103
+ }
104
+ /**
105
+ * Returns the value that associated to the number, by determining which bound contains the given number
106
+ *
107
+ * @param digit the number to retrieve
108
+ * @param defaults the default value if not found
109
+ *
110
+ * @returns the value that associated to the number, by determining which bound contains the given number
111
+ *
112
+ * @example
113
+ * ```ts
114
+ * const map = RangeMap.of([
115
+ * [[1, 50, true, true], 'white'],
116
+ * [[51, 100, false, true], 'black']
117
+ * ]);
118
+ * map.getByDigit(25); // 'white'
119
+ * map.getByDigit(50); // 'white'
120
+ * map.getByDigit(51); // undefined
121
+ * map.getByDigit(52); // 'black'
122
+ * map.getByDigit(200); // undefined
123
+ * ```
124
+ */
125
+ getByDigit(digit, defaults) {
126
+ if (this.isEmpty()) {
127
+ return defaults;
128
+ }
129
+ for (const [k, v] of this.keyMap.entries()) {
130
+ if ((v.startInclusive ? digit >= v.start : digit > v.start) && (v.endInclusive ? digit <= v.end : digit < v.end)) {
131
+ return this.valueMap.get(k);
132
+ }
133
+ }
134
+ return defaults;
135
+ }
136
+ /**
137
+ * Sets the value of the given key
138
+ *
139
+ * @param key the key to set
140
+ * @param value the value to set
141
+ * @param validation whether to compare the range to all the ranges previously, to determine if there are any conflicts
142
+ *
143
+ * @example
144
+ * ```ts
145
+ * map.set([60, 80, true, true], 'volcano');
146
+ * ```
147
+ */
148
+ set(key, value, validation = true) {
149
+ const alias = this.toInternalKey(key);
150
+ if (alias.start > alias.end || alias.start === alias.end && !alias.startInclusive && !alias.endInclusive) {
151
+ throw RangeError(`Range start ${alias.start} must be less than or equal to it's end ${alias.end}`);
152
+ }
153
+ if (validation) {
154
+ this.checkRangeConflict(alias);
155
+ }
156
+ const hash = (0, import_object_hash.default)(alias);
157
+ this.keyMap.set(hash, alias);
158
+ this.valueMap.set(hash, value);
159
+ }
160
+ /**
161
+ * Clears the map
162
+ */
163
+ clear() {
164
+ this.keyMap.clear();
165
+ this.valueMap.clear();
166
+ }
167
+ /**
168
+ * Returns the keys of the map
169
+ *
170
+ * @returns the keys of the map
171
+ */
172
+ keys() {
173
+ return [...this.keyMap.values()];
174
+ }
175
+ /**
176
+ * Returns the value array of the map
177
+ *
178
+ * @returns the value array of the map
179
+ */
180
+ values() {
181
+ return [...this.valueMap.values()];
182
+ }
183
+ /**
184
+ * Returns the key/value entries of the map
185
+ *
186
+ * @returns the key/value entries of the map
187
+ */
188
+ entries() {
189
+ if (this.isEmpty()) {
190
+ return [];
191
+ }
192
+ if (this.keyMap.size !== this.valueMap.size) {
193
+ throw EvalError(`Internal maps size mismatch!`);
194
+ }
195
+ const result = [];
196
+ for (const [k, v] of this.valueMap) {
197
+ result.push([this.keyMap.get(k), v]);
198
+ }
199
+ return result;
200
+ }
201
+ /**
202
+ * Deletes the entry with the given key
203
+ *
204
+ * @param key the key to delete
205
+ *
206
+ * @returns whether the entry has been deleted
207
+ *
208
+ * @example
209
+ * ```ts
210
+ * map.deleteByKey([1, 50]);
211
+ * ```
212
+ */
213
+ deleteByKey(key) {
214
+ if (this.isEmpty()) {
215
+ return false;
216
+ }
217
+ const hash = (0, import_object_hash.default)(this.toInternalKey(key));
218
+ return this.keyMap.delete(hash) && this.valueMap.delete(hash);
219
+ }
220
+ /**
221
+ * Deletes all the entries with the given keys
222
+ *
223
+ * @param keys the keys to delete
224
+ *
225
+ * @returns whether any of the entries has been deleted
226
+ *
227
+ * @example
228
+ * ```ts
229
+ * map.deleteByKeys([[1, 30], [30, 50]]);
230
+ * ```
231
+ */
232
+ deleteByKeys(keys) {
233
+ if (!keys.length || this.isEmpty()) {
234
+ return false;
235
+ }
236
+ let result = false;
237
+ for (const key of keys) {
238
+ if (this.deleteByKey(key)) {
239
+ result = true;
240
+ }
241
+ }
242
+ return result;
243
+ }
244
+ /**
245
+ * Deletes the entry/entries with the given value
246
+ *
247
+ * @param value the value to delete
248
+ *
249
+ * @returns whether the entry/entries has been deleted
250
+ *
251
+ * @example
252
+ * ```ts
253
+ * map.deleteByValue('red');
254
+ * ```
255
+ */
256
+ deleteByValue(value) {
257
+ if (this.isEmpty()) {
258
+ return false;
259
+ }
260
+ let result = false;
261
+ for (const [k, v] of this.valueMap.entries()) {
262
+ if (v === value && this.keyMap.delete(k) && this.valueMap.delete(k)) {
263
+ result = true;
264
+ }
265
+ }
266
+ return result;
267
+ }
268
+ /**
269
+ * Deletes all the entries with the given values
270
+ *
271
+ * @param values the values to delete
272
+ *
273
+ * @returns whether any of the entries has been deleted
274
+ *
275
+ * @example
276
+ * ```ts
277
+ * map.deleteByValues(['green', 'blue']);
278
+ * ```
279
+ */
280
+ deleteByValues(values) {
281
+ if (!values.length || this.isEmpty()) {
282
+ return false;
283
+ }
284
+ let result = false;
285
+ for (const value of values) {
286
+ if (this.deleteByValue(value)) {
287
+ result = true;
288
+ }
289
+ }
290
+ return result;
291
+ }
292
+ /**
293
+ * Processes each entry in the map
294
+ *
295
+ * @param callback a callback function that processes each entry
296
+ * @param thisArg any instance to retrieve 'this' reference in the callback function
297
+ *
298
+ * @example
299
+ * ```ts
300
+ * map.forEach((value, key) => {
301
+ * console.log(value);
302
+ * });
303
+ * ```
304
+ */
305
+ forEach(callback, thisArg) {
306
+ this.entries().forEach((entry) => {
307
+ const [k, v] = entry;
308
+ callback(v, k);
309
+ }, thisArg);
310
+ }
311
+ /**
312
+ * Processes each entry in the map with index capability
313
+ *
314
+ * @param callback a callback function that processes each entry
315
+ * @param thisArg any instance to retrieve 'this' reference in the callback function
316
+ *
317
+ * @example
318
+ * ```ts
319
+ * map.forEachIndexing((value, key, index) => {
320
+ * console.log(index);
321
+ * });
322
+ * ```
323
+ */
324
+ forEachIndexing(callback, thisArg) {
325
+ let index = 0;
326
+ this.entries().forEach((entry) => {
327
+ const [k, v] = entry;
328
+ callback(v, k, index++);
329
+ }, thisArg);
330
+ }
331
+ /**
332
+ * Processes each entry in the map with breakable capability
333
+ *
334
+ * @param callback a callback function that processes each entry. Returning false indicates to break the map iteration
335
+ * @param thisArg any instance to retrieve 'this' reference in the callback function
336
+ *
337
+ * @example
338
+ * ```ts
339
+ * map.forEachBreakable((value, key) => {
340
+ * return true;
341
+ * });
342
+ * ```
343
+ */
344
+ forEachBreakable(callback, thisArg) {
345
+ this.entries().forEach((entry) => {
346
+ const [k, v] = entry;
347
+ if (!callback(v, k)) {
348
+ return;
349
+ }
350
+ }, thisArg);
351
+ }
352
+ /**
353
+ * Returns whether the map contains the given key
354
+ *
355
+ * @param key the key to check
356
+ *
357
+ * @returns whether the map contains the given key
358
+ *
359
+ * @example
360
+ * ```ts
361
+ * map.hasKey([1, 30]);
362
+ * ```
363
+ */
364
+ hasKey(key) {
365
+ return this.isNotEmpty() && this.keyMap.has((0, import_object_hash.default)(this.toInternalKey(key)));
366
+ }
367
+ /**
368
+ * Returns whether the map contains the given key/value pair
369
+ *
370
+ * @param key the key to check
371
+ * @param value the value to check
372
+ *
373
+ * @returns whether the map contains the given key/value pair
374
+ *
375
+ * @example
376
+ * ```ts
377
+ * const map = RangeMap.of([
378
+ * [[1, 50], 'white']
379
+ * ]);
380
+ * map.hasKeyValue([1, 50], 'white'); // true
381
+ * map.hasKeyValue([1, 50], 'black'); // false
382
+ * ```
383
+ */
384
+ hasKeyValue(key, value) {
385
+ return this.isNotEmpty() && this.get(key) === value;
386
+ }
387
+ /**
388
+ * Returns whether the map contains any of the given keys
389
+ *
390
+ * @param keys the keys to check
391
+ *
392
+ * @returns whether the map contains any of the given keys
393
+ *
394
+ * @example
395
+ * ```ts
396
+ * const map = RangeMap.of([
397
+ * [[1, 50, true, true], 'white'],
398
+ * [[51, 100, false, true], 'black']
399
+ * ]);
400
+ * map.hasAnyKeys([[1, 50, true, true], [20, 60]]); // true
401
+ * ```
402
+ */
403
+ hasAnyKeys(keys) {
404
+ return this.isNotEmpty() && keys.length > 0 && keys.some((item) => this.hasKey(item));
405
+ }
406
+ /**
407
+ * Returns whether the map contains all the given keys
408
+ *
409
+ * @param keys the keys to check
410
+ *
411
+ * @returns whether the map contains all the given keys
412
+ *
413
+ * @example
414
+ * ```ts
415
+ * map.hasAllKeys([[1, 50], [51, 100]]);
416
+ * ```
417
+ */
418
+ hasAllKeys(keys) {
419
+ return this.isNotEmpty() && keys.length > 0 && keys.every((item) => this.hasKey(item));
420
+ }
421
+ /**
422
+ * Returns whether any entries of the map that contains the given values
423
+ *
424
+ * @param value the value to check
425
+ *
426
+ * @returns whether any entries of the map that contains the given values
427
+ *
428
+ * @example
429
+ * ```ts
430
+ * const map = RangeMap.of([
431
+ * [[1, 50, true, true], 'white'],
432
+ * [[51, 100, false, true], 'black']
433
+ * ]);
434
+ * map.hasValue('white'); // true
435
+ * map.hasValue('blue'); // false
436
+ * ```
437
+ */
438
+ hasValue(value) {
439
+ return this.isNotEmpty() && this.values().includes(value);
440
+ }
441
+ /**
442
+ * Returns whether the map contains any of the given values
443
+ *
444
+ * @param values the values to check
445
+ *
446
+ * @returns whether the map contains any of the given values
447
+ *
448
+ * @example
449
+ * ```ts
450
+ * const map = RangeMap.of([
451
+ * [[1, 50, true, true], 'white'],
452
+ * [[51, 100, false, true], 'black']
453
+ * ]);
454
+ * map.hasAnyValues(['red', 'black']); // true
455
+ * map.hasAnyValues(['top', 'right']); // false
456
+ * ```
457
+ */
458
+ hasAnyValues(values) {
459
+ return this.isNotEmpty() && values.length > 0 && values.some((item) => this.hasValue(item));
460
+ }
461
+ /**
462
+ * Returns whether the map contains all the given values, matching exactly
463
+ *
464
+ * @param values the values to check
465
+ *
466
+ * @returns whether the map contains all the given values, matching exactly
467
+ *
468
+ * @example
469
+ * ```ts
470
+ * map.hasAllValues(['red', 'green', 'blue']);
471
+ * ```
472
+ */
473
+ hasAllValues(values) {
474
+ return this.isNotEmpty() && values.length > 0 && values.every((item) => this.hasValue(item));
475
+ }
476
+ /**
477
+ * Returns whether the map is empty
478
+ *
479
+ * @returns whether the map is empty
480
+ */
481
+ isEmpty() {
482
+ return !this.valueMap.size;
483
+ }
484
+ /**
485
+ * Returns whether the map is not empty
486
+ *
487
+ * @returns whether the map is not empty
488
+ */
489
+ isNotEmpty() {
490
+ return this.valueMap.size > 0;
491
+ }
492
+ /**
493
+ * Response for returning the list of key/value to iterate
494
+ *
495
+ * @example
496
+ * ```ts
497
+ * for (const [key, value] of map) {
498
+ * console.log(value);
499
+ * }
500
+ * ```
501
+ */
502
+ // @ts-ignore
503
+ [Symbol.iterator]() {
504
+ return this.entries()[Symbol.iterator]();
505
+ }
506
+ /**
507
+ * Returns the size of map
508
+ *
509
+ * @returns the size of map
510
+ */
511
+ get size() {
512
+ return this.valueMap.size;
513
+ }
514
+ /**
515
+ * Returns the string representation of the map identifier ('RangeMap')
516
+ *
517
+ * @returns the string representation of the map identifier
518
+ */
519
+ get [Symbol.toStringTag]() {
520
+ return "RangeMap";
521
+ }
522
+ /**
523
+ * Returns the string representation of the map elements
524
+ *
525
+ * @returns the string representation of the map elements
526
+ *
527
+ * @example
528
+ * ```ts
529
+ * const map = RangeMap.of([
530
+ * [[1, 50, true, true], 'white'],
531
+ * [[51, 100, false, true], 'black']
532
+ * ]);
533
+ * console.log(map.toString()); // '[start:1,end:50,startInclusive:true,endInclusive:true]:white;[start:51,end:100,startInclusive:false,endInclusive:true]:black'
534
+ * ```
535
+ */
536
+ toString() {
537
+ return [...this].map((entry) => {
538
+ const [k, v] = entry;
539
+ const ks = Object.keys(k).map((item) => `${item}:${k[item]}`).join();
540
+ return `[${ks}]:${v}`;
541
+ }).join(";");
542
+ }
543
+ /**
544
+ * Converts the given key to internal one, for storage
545
+ *
546
+ * @param key the key to convert
547
+ *
548
+ * @returns the converted key
549
+ */
550
+ toInternalKey(key) {
551
+ return !Array.isArray(key) ? key : {
552
+ start: key.length > 0 ? key[0] : 0,
553
+ end: key.length > 1 ? key[1] : 0,
554
+ startInclusive: key.length > 2 ? key[2] : true,
555
+ endInclusive: key.length > 3 ? key[3] : false
556
+ };
557
+ }
558
+ /**
559
+ * Checks the given key is conflicting with the ranges previously
560
+ *
561
+ * @param key the key to inspect
562
+ */
563
+ checkRangeConflict(key) {
564
+ if (this.isEmpty()) {
565
+ return;
566
+ }
567
+ const keyExpress = `${key.startInclusive ? "[" : "("}${key.start},${key.end}${key.endInclusive ? "]" : ")"}`;
568
+ for (const k of this.keyMap.values()) {
569
+ const kExpress = `${k.startInclusive ? "[" : "("}${k.start},${k.end}${k.endInclusive ? "]" : ")"}`;
570
+ if (key.start <= k.start && key.end >= k.end) {
571
+ throw RangeError(`Range ${keyExpress} must not override the range ${kExpress}`);
572
+ }
573
+ const badStart = (key.startInclusive ? key.start >= k.start : key.start > k.start) && (key.startInclusive && k.endInclusive ? key.start <= k.end : key.start < k.end);
574
+ const badEnd = (key.endInclusive && k.startInclusive ? key.end >= k.start : key.end > k.start) && key.end <= k.end;
575
+ if (badStart || badEnd) {
576
+ throw RangeError(`Range ${keyExpress} must not intersect the range ${kExpress}`);
577
+ }
578
+ }
579
+ }
580
+ };
581
+ // Annotate the CommonJS export names for ESM import in node:
582
+ 0 && (module.exports = {
583
+ RangeMap
584
+ });
@@ -0,0 +1,27 @@
1
+ import { type MultiKeyMapEntries } from "..";
2
+ export declare class ReadonlyMultiKeyMap<K, V> implements Omit<ReadonlyMap<K[], V>, 'forEach' | 'get' | 'has' | 'entries' | 'keys' | 'values'> {
3
+ private readonly map;
4
+ static of<K, V>(entries?: MultiKeyMapEntries<K, V>): ReadonlyMultiKeyMap<K, V>;
5
+ constructor(entries?: MultiKeyMapEntries<K, V>);
6
+ get(keys: K[], defaults?: V): V | undefined;
7
+ keys(): K[][];
8
+ values(): V[];
9
+ entries(): [K[], V][];
10
+ forEach(callback: (value?: V, keys?: K[]) => void, thisArg?: any): void;
11
+ forEachIndexing(callback: (value?: V, keys?: K[], index?: number) => void, thisArg?: any): void;
12
+ forEachBreakable(callback: (value?: V, keys?: K[]) => boolean, thisArg?: any): void;
13
+ hasKey(keys: K[], exact?: boolean): boolean;
14
+ hasKeyValue(keys: K[], value: V): boolean;
15
+ hasAnyKeys(keys: K[][], exact?: boolean): boolean;
16
+ hasAllKeys(keys: K[][], exact?: boolean): boolean;
17
+ hasValue(value: V): boolean;
18
+ hasAnyValues(values: V[]): boolean;
19
+ hasAllValues(values: V[]): boolean;
20
+ isEmpty(): boolean;
21
+ isNotEmpty(): boolean;
22
+ getKey(value: V, defaults?: K[]): K[] | undefined;
23
+ [Symbol.iterator](): IterableIterator<[K[], V]>;
24
+ get size(): number;
25
+ get [Symbol.toStringTag](): string;
26
+ toString(): string;
27
+ }