directed-graph-typed 1.48.0 → 1.49.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 (89) hide show
  1. package/dist/data-structures/base/index.d.ts +1 -0
  2. package/dist/data-structures/base/index.js +17 -0
  3. package/dist/data-structures/base/iterable-base.d.ts +232 -0
  4. package/dist/data-structures/base/iterable-base.js +312 -0
  5. package/dist/data-structures/binary-tree/avl-tree.d.ts +28 -19
  6. package/dist/data-structures/binary-tree/avl-tree.js +22 -11
  7. package/dist/data-structures/binary-tree/binary-tree.d.ts +158 -152
  8. package/dist/data-structures/binary-tree/binary-tree.js +241 -215
  9. package/dist/data-structures/binary-tree/bst.d.ts +64 -48
  10. package/dist/data-structures/binary-tree/bst.js +94 -65
  11. package/dist/data-structures/binary-tree/rb-tree.d.ts +39 -39
  12. package/dist/data-structures/binary-tree/rb-tree.js +42 -49
  13. package/dist/data-structures/binary-tree/tree-multimap.d.ts +60 -34
  14. package/dist/data-structures/binary-tree/tree-multimap.js +59 -27
  15. package/dist/data-structures/graph/abstract-graph.d.ts +92 -53
  16. package/dist/data-structures/graph/abstract-graph.js +130 -103
  17. package/dist/data-structures/graph/directed-graph.d.ts +70 -52
  18. package/dist/data-structures/graph/directed-graph.js +111 -65
  19. package/dist/data-structures/graph/map-graph.d.ts +5 -5
  20. package/dist/data-structures/graph/map-graph.js +8 -8
  21. package/dist/data-structures/graph/undirected-graph.d.ts +51 -32
  22. package/dist/data-structures/graph/undirected-graph.js +117 -54
  23. package/dist/data-structures/hash/hash-map.d.ts +160 -44
  24. package/dist/data-structures/hash/hash-map.js +314 -82
  25. package/dist/data-structures/heap/heap.d.ts +50 -7
  26. package/dist/data-structures/heap/heap.js +60 -30
  27. package/dist/data-structures/index.d.ts +1 -0
  28. package/dist/data-structures/index.js +1 -0
  29. package/dist/data-structures/linked-list/doubly-linked-list.d.ts +42 -55
  30. package/dist/data-structures/linked-list/doubly-linked-list.js +50 -77
  31. package/dist/data-structures/linked-list/singly-linked-list.d.ts +36 -55
  32. package/dist/data-structures/linked-list/singly-linked-list.js +44 -77
  33. package/dist/data-structures/queue/deque.d.ts +35 -167
  34. package/dist/data-structures/queue/deque.js +43 -249
  35. package/dist/data-structures/queue/queue.d.ts +49 -48
  36. package/dist/data-structures/queue/queue.js +69 -82
  37. package/dist/data-structures/stack/stack.d.ts +43 -10
  38. package/dist/data-structures/stack/stack.js +50 -31
  39. package/dist/data-structures/trie/trie.d.ts +41 -6
  40. package/dist/data-structures/trie/trie.js +53 -32
  41. package/dist/interfaces/binary-tree.d.ts +6 -6
  42. package/dist/types/common.d.ts +11 -8
  43. package/dist/types/common.js +6 -1
  44. package/dist/types/data-structures/base/base.d.ts +5 -0
  45. package/dist/types/data-structures/base/base.js +2 -0
  46. package/dist/types/data-structures/base/index.d.ts +1 -0
  47. package/dist/types/data-structures/base/index.js +17 -0
  48. package/dist/types/data-structures/binary-tree/avl-tree.d.ts +3 -3
  49. package/dist/types/data-structures/binary-tree/binary-tree.d.ts +4 -4
  50. package/dist/types/data-structures/binary-tree/bst.d.ts +6 -6
  51. package/dist/types/data-structures/binary-tree/rb-tree.d.ts +3 -3
  52. package/dist/types/data-structures/binary-tree/tree-multimap.d.ts +3 -3
  53. package/dist/types/data-structures/hash/hash-map.d.ts +4 -0
  54. package/dist/types/data-structures/index.d.ts +1 -0
  55. package/dist/types/data-structures/index.js +1 -0
  56. package/package.json +2 -2
  57. package/src/data-structures/base/index.ts +1 -0
  58. package/src/data-structures/base/iterable-base.ts +329 -0
  59. package/src/data-structures/binary-tree/avl-tree.ts +37 -25
  60. package/src/data-structures/binary-tree/binary-tree.ts +336 -296
  61. package/src/data-structures/binary-tree/bst.ts +135 -89
  62. package/src/data-structures/binary-tree/rb-tree.ts +60 -69
  63. package/src/data-structures/binary-tree/tree-multimap.ts +86 -49
  64. package/src/data-structures/graph/abstract-graph.ts +136 -104
  65. package/src/data-structures/graph/directed-graph.ts +114 -65
  66. package/src/data-structures/graph/map-graph.ts +8 -8
  67. package/src/data-structures/graph/undirected-graph.ts +124 -56
  68. package/src/data-structures/hash/hash-map.ts +335 -84
  69. package/src/data-structures/heap/heap.ts +63 -36
  70. package/src/data-structures/index.ts +1 -0
  71. package/src/data-structures/linked-list/doubly-linked-list.ts +54 -83
  72. package/src/data-structures/linked-list/singly-linked-list.ts +49 -84
  73. package/src/data-structures/queue/deque.ts +43 -275
  74. package/src/data-structures/queue/queue.ts +71 -86
  75. package/src/data-structures/stack/stack.ts +53 -34
  76. package/src/data-structures/trie/trie.ts +58 -35
  77. package/src/interfaces/binary-tree.ts +5 -6
  78. package/src/types/common.ts +11 -8
  79. package/src/types/data-structures/base/base.ts +6 -0
  80. package/src/types/data-structures/base/index.ts +1 -0
  81. package/src/types/data-structures/binary-tree/avl-tree.ts +3 -3
  82. package/src/types/data-structures/binary-tree/binary-tree.ts +6 -5
  83. package/src/types/data-structures/binary-tree/bst.ts +6 -6
  84. package/src/types/data-structures/binary-tree/rb-tree.ts +3 -3
  85. package/src/types/data-structures/binary-tree/tree-multimap.ts +3 -3
  86. package/src/types/data-structures/hash/hash-map.ts +2 -0
  87. package/src/types/data-structures/heap/heap.ts +1 -1
  88. package/src/types/data-structures/index.ts +1 -0
  89. package/src/types/data-structures/priority-queue/priority-queue.ts +1 -1
@@ -10,8 +10,8 @@ import {
10
10
  BiTreeDeleteResult,
11
11
  BSTNodeKeyOrNode,
12
12
  BTNCallback,
13
- BTNKey,
14
13
  BTNodeExemplar,
14
+ BTNodeKeyOrNode,
15
15
  IterationType,
16
16
  RBTNColor,
17
17
  RBTreeOptions,
@@ -22,13 +22,13 @@ import { BST, BSTNode } from './bst';
22
22
  import { IBinaryTree } from '../../interfaces';
23
23
  import { BinaryTreeNode } from './binary-tree';
24
24
 
25
- export class RedBlackTreeNode<V = any, N extends RedBlackTreeNode<V, N> = RedBlackTreeNodeNested<V>> extends BSTNode<
26
- V,
25
+ export class RedBlackTreeNode<K = any, V = any, N extends RedBlackTreeNode<K, V, N> = RedBlackTreeNodeNested<K, V>> extends BSTNode<
26
+ K, V,
27
27
  N
28
28
  > {
29
29
  color: RBTNColor;
30
30
 
31
- constructor(key: BTNKey, value?: V, color: RBTNColor = RBTNColor.BLACK) {
31
+ constructor(key: K, value?: V, color: RBTNColor = RBTNColor.BLACK) {
32
32
  super(key, value);
33
33
  this.color = color;
34
34
  }
@@ -41,15 +41,15 @@ export class RedBlackTreeNode<V = any, N extends RedBlackTreeNode<V, N> = RedBla
41
41
  * 4. Red nodes must have black children.
42
42
  * 5. Black balance: Every path from any node to each of its leaf nodes contains the same number of black nodes.
43
43
  */
44
- export class RedBlackTree<V = any, N extends RedBlackTreeNode<V, N> = RedBlackTreeNode<V, RedBlackTreeNodeNested<V>>, TREE extends RedBlackTree<V, N, TREE> = RedBlackTree<V, N, RedBlackTreeNested<V, N>>>
45
- extends BST<V, N, TREE>
46
- implements IBinaryTree<V, N, TREE> {
47
- Sentinel: N = new RedBlackTreeNode<V>(NaN) as unknown as N;
44
+ export class RedBlackTree<K = any, V = any, N extends RedBlackTreeNode<K, V, N> = RedBlackTreeNode<K, V, RedBlackTreeNodeNested<K, V>>, TREE extends RedBlackTree<K, V, N, TREE> = RedBlackTree<K, V, N, RedBlackTreeNested<K, V, N>>>
45
+ extends BST<K, V, N, TREE>
46
+ implements IBinaryTree<K, V, N, TREE> {
47
+ Sentinel: N = new RedBlackTreeNode<K, V>(NaN as K) as unknown as N;
48
48
 
49
49
  /**
50
50
  * This is the constructor function for a Red-Black Tree data structure in TypeScript, which
51
51
  * initializes the tree with optional elements and options.
52
- * @param [elements] - The `elements` parameter is an optional iterable of `BTNodeExemplar<V, N>`
52
+ * @param [elements] - The `elements` parameter is an optional iterable of `BTNodeExemplar<K, V, N>`
53
53
  * objects. It represents the initial elements that will be added to the RBTree during its
54
54
  * construction. If this parameter is provided, the `addMany` method is called to add all the
55
55
  * elements to the
@@ -57,7 +57,7 @@ export class RedBlackTree<V = any, N extends RedBlackTreeNode<V, N> = RedBlackTr
57
57
  * behavior of the RBTree. It is of type `Partial<RBTreeOptions>`, which means that you can provide
58
58
  * only a subset of the properties defined in the `RBTreeOptions` interface.
59
59
  */
60
- constructor(elements?: Iterable<BTNodeExemplar<V, N>>, options?: Partial<RBTreeOptions>) {
60
+ constructor(elements?: Iterable<BTNodeExemplar<K, V, N>>, options?: Partial<RBTreeOptions<K>>) {
61
61
  super([], options);
62
62
 
63
63
  this._root = this.Sentinel;
@@ -78,7 +78,7 @@ export class RedBlackTree<V = any, N extends RedBlackTreeNode<V, N> = RedBlackTr
78
78
 
79
79
  /**
80
80
  * The function creates a new Red-Black Tree node with the specified key, value, and color.
81
- * @param {BTNKey} key - The key parameter is the key value associated with the node. It is used to
81
+ * @param {K} key - The key parameter is the key value associated with the node. It is used to
82
82
  * identify and compare nodes in the Red-Black Tree.
83
83
  * @param {V} [value] - The `value` parameter is an optional parameter that represents the value
84
84
  * associated with the node. It is of type `V`, which is a generic type that can be replaced with any
@@ -88,8 +88,8 @@ export class RedBlackTree<V = any, N extends RedBlackTreeNode<V, N> = RedBlackTr
88
88
  * @returns The method is returning a new instance of a RedBlackTreeNode with the specified key,
89
89
  * value, and color.
90
90
  */
91
- override createNode(key: BTNKey, value?: V, color: RBTNColor = RBTNColor.BLACK): N {
92
- return new RedBlackTreeNode<V, N>(key, value, color) as N;
91
+ override createNode(key: K, value?: V, color: RBTNColor = RBTNColor.BLACK): N {
92
+ return new RedBlackTreeNode<K, V, N>(key, value, color) as N;
93
93
  }
94
94
 
95
95
  /**
@@ -99,32 +99,42 @@ export class RedBlackTree<V = any, N extends RedBlackTreeNode<V, N> = RedBlackTr
99
99
  * class.
100
100
  * @returns a new instance of a RedBlackTree object.
101
101
  */
102
- override createTree(options?: RBTreeOptions): TREE {
103
- return new RedBlackTree<V, N, TREE>([], {
102
+ override createTree(options?: RBTreeOptions<K>): TREE {
103
+ return new RedBlackTree<K, V, N, TREE>([], {
104
104
  iterationType: this.iterationType,
105
- comparator: this.comparator, ...options
105
+ variant: this.variant, ...options
106
106
  }) as TREE;
107
107
  }
108
108
 
109
109
  /**
110
110
  * The function checks if an exemplar is an instance of the RedBlackTreeNode class.
111
- * @param exemplar - The `exemplar` parameter is of type `BTNodeExemplar<V, N>`.
111
+ * @param exemplar - The `exemplar` parameter is of type `BTNodeExemplar<K, V, N>`.
112
112
  * @returns a boolean value indicating whether the exemplar is an instance of the RedBlackTreeNode
113
113
  * class.
114
114
  */
115
- override isNode(exemplar: BTNodeExemplar<V, N>): exemplar is N {
115
+ override isNode(exemplar: BTNodeExemplar<K, V, N>): exemplar is N {
116
116
  return exemplar instanceof RedBlackTreeNode;
117
117
  }
118
118
 
119
119
  /**
120
- * The function `exemplarToNode` takes an exemplar and returns a node if the exemplar is valid,
121
- * otherwise it returns undefined.
122
- * @param exemplar - BTNodeExemplar<V, N> - A generic type representing an exemplar of a binary tree
123
- * node. It can be either a node itself, an entry (key-value pair), a node key, or any other value
124
- * that is not a valid exemplar.
125
- * @returns a variable `node` which is of type `N | undefined`.
120
+ * The function "isNotNodeInstance" checks if a potential key is a K.
121
+ * @param {any} potentialKey - The potentialKey parameter is of type any, which means it can be any
122
+ * data type.
123
+ * @returns a boolean value indicating whether the potentialKey is of type number or not.
126
124
  */
127
- override exemplarToNode(exemplar: BTNodeExemplar<V, N>): N | undefined {
125
+ override isNotNodeInstance(potentialKey: BTNodeKeyOrNode<K, N>): potentialKey is K {
126
+ return !(potentialKey instanceof RedBlackTreeNode)
127
+ }
128
+
129
+ /**
130
+ * The function `exemplarToNode` takes an exemplar and converts it into a node object if possible.
131
+ * @param exemplar - The `exemplar` parameter is of type `BTNodeExemplar<K, V, N>`, where:
132
+ * @param {V} [value] - The `value` parameter is an optional value that can be passed to the
133
+ * `exemplarToNode` function. It represents the value associated with the exemplar node. If a value
134
+ * is provided, it will be used when creating the new node. If no value is provided, the new node
135
+ * @returns a node of type N or undefined.
136
+ */
137
+ override exemplarToNode(exemplar: BTNodeExemplar<K, V, N>, value?: V): N | undefined {
128
138
  let node: N | undefined;
129
139
 
130
140
  if (exemplar === null || exemplar === undefined) {
@@ -138,8 +148,8 @@ export class RedBlackTree<V = any, N extends RedBlackTreeNode<V, N> = RedBlackTr
138
148
  } else {
139
149
  node = this.createNode(key, value, RBTNColor.RED);
140
150
  }
141
- } else if (this.isNodeKey(exemplar)) {
142
- node = this.createNode(exemplar, undefined, RBTNColor.RED);
151
+ } else if (this.isNotNodeInstance(exemplar)) {
152
+ node = this.createNode(exemplar, value, RBTNColor.RED);
143
153
  } else {
144
154
  return;
145
155
  }
@@ -152,13 +162,19 @@ export class RedBlackTree<V = any, N extends RedBlackTreeNode<V, N> = RedBlackTr
152
162
  */
153
163
 
154
164
  /**
155
- * The function adds a node to a Red-Black Tree data structure.
156
- * @param keyOrNodeOrEntry - The `keyOrNodeOrEntry` parameter can be one of the following:
157
- * @returns The method `add` returns either an instance of `N` (the node that was added) or
158
- * `undefined`.
165
+ * Time Complexity: O(log n) on average (where n is the number of nodes in the tree)
166
+ * Space Complexity: O(1)
167
+ *
168
+ * The `add` function adds a new node to a binary search tree and performs necessary rotations and
169
+ * color changes to maintain the red-black tree properties.
170
+ * @param keyOrNodeOrEntry - The `keyOrNodeOrEntry` parameter can be either a key, a node, or an
171
+ * entry.
172
+ * @param {V} [value] - The `value` parameter represents the value associated with the key that is
173
+ * being added to the binary search tree.
174
+ * @returns The method `add` returns either the newly added node (`N`) or `undefined`.
159
175
  */
160
- override add(keyOrNodeOrEntry: BTNodeExemplar<V, N>): N | undefined {
161
- const newNode = this.exemplarToNode(keyOrNodeOrEntry);
176
+ override add(keyOrNodeOrEntry: BTNodeExemplar<K, V, N>, value?: V): N | undefined {
177
+ const newNode = this.exemplarToNode(keyOrNodeOrEntry, value);
162
178
  if (newNode === undefined) return;
163
179
 
164
180
  newNode.left = this.Sentinel;
@@ -295,11 +311,12 @@ export class RedBlackTree<V = any, N extends RedBlackTreeNode<V, N> = RedBlackTr
295
311
  */
296
312
 
297
313
  override isRealNode(node: N | undefined): node is N {
298
- return node !== this.Sentinel && node !== undefined;
314
+ if (node === this.Sentinel || node === undefined) return false;
315
+ return node instanceof RedBlackTreeNode;
299
316
  }
300
317
 
301
- getNode<C extends BTNCallback<N, BTNKey>>(
302
- identifier: BTNKey,
318
+ getNode<C extends BTNCallback<N, K>>(
319
+ identifier: K,
303
320
  callback?: C,
304
321
  beginRoot?: N | undefined,
305
322
  iterationType?: IterationType
@@ -337,7 +354,7 @@ export class RedBlackTree<V = any, N extends RedBlackTreeNode<V, N> = RedBlackTr
337
354
  * @param {C} callback - The `callback` parameter is a function that will be called for each node in
338
355
  * the binary tree. It is used to determine if a node matches the given identifier. The `callback`
339
356
  * function should take a single parameter of type `N` (the type of the nodes in the binary tree) and
340
- * @param {BTNKey | N | undefined} beginRoot - The `beginRoot` parameter is the starting point for
357
+ * @param {K | N | undefined} beginRoot - The `beginRoot` parameter is the starting point for
341
358
  * searching for a node in a binary tree. It can be either a key value or a node object. If it is not
342
359
  * provided, the search will start from the root of the binary tree.
343
360
  * @param iterationType - The `iterationType` parameter is a variable that determines the type of
@@ -348,7 +365,7 @@ export class RedBlackTree<V = any, N extends RedBlackTreeNode<V, N> = RedBlackTr
348
365
  getNode<C extends BTNCallback<N>>(
349
366
  identifier: ReturnType<C> | undefined,
350
367
  callback: C = this._defaultOneParamCallback as C,
351
- beginRoot: BSTNodeKeyOrNode<N> = this.root,
368
+ beginRoot: BSTNodeKeyOrNode<K, N> = this.root,
352
369
  iterationType = this.iterationType
353
370
  ): N | null | undefined {
354
371
  if ((identifier as any) instanceof BinaryTreeNode) callback = (node => node) as C;
@@ -357,38 +374,12 @@ export class RedBlackTree<V = any, N extends RedBlackTreeNode<V, N> = RedBlackTr
357
374
  }
358
375
 
359
376
  /**
360
- * Time Complexity: O(log n) on average (where n is the number of nodes in the tree)
377
+ * Time Complexity: O(log n)
361
378
  * Space Complexity: O(1)
362
379
  */
363
380
 
364
381
  /**
365
- * Time Complexity: O(log n) on average (where n is the number of nodes in the tree)
366
- * Space Complexity: O(1)
367
- *
368
- * The function returns the successor of a given node in a red-black tree.
369
- * @param {RedBlackTreeNode} x - RedBlackTreeNode - The node for which we want to find the successor.
370
- * @returns the successor of the given RedBlackTreeNode.
371
- */
372
- override getSuccessor(x: N): N | undefined {
373
- if (x.right !== this.Sentinel) {
374
- return this.getLeftMost(x.right) ?? undefined;
375
- }
376
-
377
- let y: N | undefined = x.parent;
378
- while (y !== this.Sentinel && y !== undefined && x === y.right) {
379
- x = y;
380
- y = y.parent;
381
- }
382
- return y;
383
- }
384
-
385
- /**
386
- * Time Complexity: O(log n) on average (where n is the number of nodes in the tree)
387
- * Space Complexity: O(1)
388
- */
389
-
390
- /**
391
- * Time Complexity: O(log n) on average (where n is the number of nodes in the tree)
382
+ * Time Complexity: O(log n)
392
383
  * Space Complexity: O(1)
393
384
  *
394
385
  * The function returns the predecessor of a given node in a red-black tree.
@@ -397,12 +388,12 @@ export class RedBlackTree<V = any, N extends RedBlackTreeNode<V, N> = RedBlackTr
397
388
  * @returns the predecessor of the given RedBlackTreeNode 'x'.
398
389
  */
399
390
  override getPredecessor(x: N): N {
400
- if (x.left !== this.Sentinel) {
401
- return this.getRightMost(x.left!)!;
391
+ if (this.isRealNode(x.left)) {
392
+ return this.getRightMost(x.left)!;
402
393
  }
403
394
 
404
395
  let y: N | undefined = x.parent;
405
- while (y !== this.Sentinel && x === y!.left) {
396
+ while (this.isRealNode(y) && x === y.left) {
406
397
  x = y!;
407
398
  y = y!.parent;
408
399
  }
@@ -5,26 +5,28 @@
5
5
  * @copyright Copyright (c) 2022 Tyler Zeng <zrwusa@gmail.com>
6
6
  * @license MIT License
7
7
  */
8
- import type {
9
- BSTNodeKeyOrNode,
10
- BTNKey,
11
- BTNodeExemplar,
12
- TreeMultimapNodeNested,
13
- TreeMultimapOptions
8
+ import type { BSTNodeKeyOrNode, BTNodeExemplar, TreeMultimapNodeNested, TreeMultimapOptions } from '../../types';
9
+ import {
10
+ BiTreeDeleteResult,
11
+ BTNCallback,
12
+ BTNodeKeyOrNode,
13
+ FamilyPosition,
14
+ IterationType,
15
+ TreeMultimapNested
14
16
  } from '../../types';
15
- import { BiTreeDeleteResult, BTNCallback, FamilyPosition, IterationType, TreeMultimapNested } from '../../types';
16
17
  import { IBinaryTree } from '../../interfaces';
17
18
  import { AVLTree, AVLTreeNode } from './avl-tree';
18
19
 
19
20
  export class TreeMultimapNode<
21
+ K = any,
20
22
  V = any,
21
- N extends TreeMultimapNode<V, N> = TreeMultimapNodeNested<V>
22
- > extends AVLTreeNode<V, N> {
23
+ N extends TreeMultimapNode<K, V, N> = TreeMultimapNodeNested<K, V>
24
+ > extends AVLTreeNode<K, V, N> {
23
25
  count: number;
24
26
 
25
27
  /**
26
28
  * The constructor function initializes a BinaryTreeNode object with a key, value, and count.
27
- * @param {BTNKey} key - The `key` parameter is of type `BTNKey` and represents the unique identifier
29
+ * @param {K} key - The `key` parameter is of type `K` and represents the unique identifier
28
30
  * of the binary tree node.
29
31
  * @param {V} [value] - The `value` parameter is an optional parameter of type `V`. It represents the value of the binary
30
32
  * tree node. If no value is provided, it will be `undefined`.
@@ -32,7 +34,7 @@ export class TreeMultimapNode<
32
34
  * occurs in a binary tree node. It has a default value of 1, which means that if no value is provided for the `count`
33
35
  * parameter when creating a new instance of the `BinaryTreeNode` class.
34
36
  */
35
- constructor(key: BTNKey, value?: V, count = 1) {
37
+ constructor(key: K, value?: V, count = 1) {
36
38
  super(key, value);
37
39
  this.count = count;
38
40
  }
@@ -41,12 +43,12 @@ export class TreeMultimapNode<
41
43
  /**
42
44
  * The only distinction between a TreeMultimap and a AVLTree lies in the ability of the former to store duplicate nodes through the utilization of counters.
43
45
  */
44
- export class TreeMultimap<V = any, N extends TreeMultimapNode<V, N> = TreeMultimapNode<V, TreeMultimapNodeNested<V>>,
45
- TREE extends TreeMultimap<V, N, TREE> = TreeMultimap<V, N, TreeMultimapNested<V, N>>>
46
- extends AVLTree<V, N, TREE>
47
- implements IBinaryTree<V, N, TREE> {
46
+ export class TreeMultimap<K = any, V = any, N extends TreeMultimapNode<K, V, N> = TreeMultimapNode<K, V, TreeMultimapNodeNested<K, V>>,
47
+ TREE extends TreeMultimap<K, V, N, TREE> = TreeMultimap<K, V, N, TreeMultimapNested<K, V, N>>>
48
+ extends AVLTree<K, V, N, TREE>
49
+ implements IBinaryTree<K, V, N, TREE> {
48
50
 
49
- constructor(elements?: Iterable<BTNodeExemplar<V, N>>, options?: Partial<TreeMultimapOptions>) {
51
+ constructor(elements?: Iterable<BTNodeExemplar<K, V, N>>, options?: Partial<TreeMultimapOptions<K>>) {
50
52
  super([], options);
51
53
  if (elements) this.addMany(elements);
52
54
  }
@@ -62,43 +64,56 @@ export class TreeMultimap<V = any, N extends TreeMultimapNode<V, N> = TreeMultim
62
64
 
63
65
  /**
64
66
  * The function creates a new BSTNode with the given key, value, and count.
65
- * @param {BTNKey} key - The key parameter is the unique identifier for the binary tree node. It is used to
67
+ * @param {K} key - The key parameter is the unique identifier for the binary tree node. It is used to
66
68
  * distinguish one node from another in the tree.
67
69
  * @param {N} value - The `value` parameter represents the value that will be stored in the binary search tree node.
68
70
  * @param {number} [count] - The "count" parameter is an optional parameter of type number. It represents the number of
69
71
  * occurrences of the value in the binary search tree node. If not provided, the count will default to 1.
70
72
  * @returns A new instance of the BSTNode class with the specified key, value, and count (if provided).
71
73
  */
72
- override createNode(key: BTNKey, value?: V, count?: number): N {
74
+ override createNode(key: K, value?: V, count?: number): N {
73
75
  return new TreeMultimapNode(key, value, count) as N;
74
76
  }
75
77
 
76
- override createTree(options?: TreeMultimapOptions): TREE {
77
- return new TreeMultimap<V, N, TREE>([], {
78
+ override createTree(options?: TreeMultimapOptions<K>): TREE {
79
+ return new TreeMultimap<K, V, N, TREE>([], {
78
80
  iterationType: this.iterationType,
79
- comparator: this.comparator, ...options
81
+ variant: this.variant, ...options
80
82
  }) as TREE;
81
83
  }
82
84
 
83
85
  /**
84
86
  * The function checks if an exemplar is an instance of the TreeMultimapNode class.
85
- * @param exemplar - The `exemplar` parameter is of type `BTNodeExemplar<V, N>`.
87
+ * @param exemplar - The `exemplar` parameter is of type `BTNodeExemplar<K, V, N>`.
86
88
  * @returns a boolean value indicating whether the exemplar is an instance of the TreeMultimapNode
87
89
  * class.
88
90
  */
89
- override isNode(exemplar: BTNodeExemplar<V, N>): exemplar is N {
91
+ override isNode(exemplar: BTNodeExemplar<K, V, N>): exemplar is N {
90
92
  return exemplar instanceof TreeMultimapNode;
91
93
  }
92
94
 
95
+ /**
96
+ * The function "isNotNodeInstance" checks if a potential key is a K.
97
+ * @param {any} potentialKey - The potentialKey parameter is of type any, which means it can be any
98
+ * data type.
99
+ * @returns a boolean value indicating whether the potentialKey is of type number or not.
100
+ */
101
+ override isNotNodeInstance(potentialKey: BTNodeKeyOrNode<K, N>): potentialKey is K {
102
+ return !(potentialKey instanceof TreeMultimapNode)
103
+ }
104
+
93
105
  /**
94
106
  * The function `exemplarToNode` converts an exemplar object into a node object.
95
- * @param exemplar - The `exemplar` parameter is of type `BTNodeExemplar<V, N>`, where `V` represents
96
- * the value type and `N` represents the node type.
107
+ * @param exemplar - The `exemplar` parameter is of type `BTNodeExemplar<K, V, N>`, which means it
108
+ * can be one of the following:
109
+ * @param {V} [value] - The `value` parameter is an optional argument that represents the value
110
+ * associated with the node. It is of type `V`, which can be any data type. If no value is provided,
111
+ * it defaults to `undefined`.
97
112
  * @param [count=1] - The `count` parameter is an optional parameter that specifies the number of
98
- * times the node should be created. If not provided, it defaults to 1.
99
- * @returns a value of type `N` (the generic type parameter) or `undefined`.
113
+ * times the value should be added to the node. If not provided, it defaults to 1.
114
+ * @returns a node of type `N` or `undefined`.
100
115
  */
101
- override exemplarToNode(exemplar: BTNodeExemplar<V, N>, count = 1): N | undefined {
116
+ override exemplarToNode(exemplar: BTNodeExemplar<K, V, N>, value?: V, count = 1): N | undefined {
102
117
  let node: N | undefined;
103
118
  if (exemplar === undefined || exemplar === null) {
104
119
  return;
@@ -111,8 +126,8 @@ export class TreeMultimap<V = any, N extends TreeMultimapNode<V, N> = TreeMultim
111
126
  } else {
112
127
  node = this.createNode(key, value, count);
113
128
  }
114
- } else if (this.isNodeKey(exemplar)) {
115
- node = this.createNode(exemplar, undefined, count);
129
+ } else if (this.isNotNodeInstance(exemplar)) {
130
+ node = this.createNode(exemplar, value, count);
116
131
  } else {
117
132
  return;
118
133
  }
@@ -128,16 +143,20 @@ export class TreeMultimap<V = any, N extends TreeMultimapNode<V, N> = TreeMultim
128
143
  * Time Complexity: O(log n) - logarithmic time, where "n" is the number of nodes in the tree. The add method of the superclass (AVLTree) has logarithmic time complexity.
129
144
  * Space Complexity: O(1) - constant space, as it doesn't use additional data structures that scale with input size.
130
145
  *
131
- * The `add` function overrides the base class `add` function to add a new node to the tree multimap
132
- * and update the count.
133
- * @param keyOrNodeOrEntry - The `keyOrNodeOrEntry` parameter can be one of the following:
134
- * @param [count=1] - The `count` parameter is an optional parameter that specifies the number of
135
- * times the key or node or entry should be added to the multimap. If not provided, the default value
136
- * is 1.
137
- * @returns either a node (`N`) or `undefined`.
146
+ * The function overrides the add method of a binary tree node and adds a new node to the tree.
147
+ * @param keyOrNodeOrEntry - The `keyOrNodeOrEntry` parameter can be either a key, a node, or an
148
+ * entry. It represents the key, node, or entry that you want to add to the binary tree.
149
+ * @param {V} [value] - The `value` parameter represents the value associated with the key in the
150
+ * binary tree node. It is an optional parameter, meaning it can be omitted when calling the `add`
151
+ * method.
152
+ * @param [count=1] - The `count` parameter represents the number of times the key-value pair should
153
+ * be added to the binary tree. By default, it is set to 1, meaning that the key-value pair will be
154
+ * added once. However, you can specify a different value for `count` if you want to add
155
+ * @returns The method is returning either the newly inserted node or `undefined` if the insertion
156
+ * was not successful.
138
157
  */
139
- override add(keyOrNodeOrEntry: BTNodeExemplar<V, N>, count = 1): N | undefined {
140
- const newNode = this.exemplarToNode(keyOrNodeOrEntry, count);
158
+ override add(keyOrNodeOrEntry: BTNodeExemplar<K, V, N>, value?: V, count = 1): N | undefined {
159
+ const newNode = this.exemplarToNode(keyOrNodeOrEntry, value, count);
141
160
  if (newNode === undefined) return;
142
161
 
143
162
  const orgNodeCount = newNode?.count || 0;
@@ -163,7 +182,7 @@ export class TreeMultimap<V = any, N extends TreeMultimapNode<V, N> = TreeMultim
163
182
  * either keys, nodes, or entries.
164
183
  * @returns The method is returning an array of type `N | undefined`.
165
184
  */
166
- override addMany(keysOrNodesOrEntries: Iterable<BTNodeExemplar<V, N>>): (N | undefined)[] {
185
+ override addMany(keysOrNodesOrEntries: Iterable<BTNodeExemplar<K, V, N>>): (N | undefined)[] {
167
186
  return super.addMany(keysOrNodesOrEntries);
168
187
  }
169
188
 
@@ -195,7 +214,7 @@ export class TreeMultimap<V = any, N extends TreeMultimapNode<V, N> = TreeMultim
195
214
  if (l > r) return;
196
215
  const m = l + Math.floor((r - l) / 2);
197
216
  const midNode = sorted[m];
198
- this.add([midNode.key, midNode.value], midNode.count);
217
+ this.add(midNode.key, midNode.value, midNode.count);
199
218
  buildBalanceBST(l, m - 1);
200
219
  buildBalanceBST(m + 1, r);
201
220
  };
@@ -211,7 +230,7 @@ export class TreeMultimap<V = any, N extends TreeMultimapNode<V, N> = TreeMultim
211
230
  if (l <= r) {
212
231
  const m = l + Math.floor((r - l) / 2);
213
232
  const midNode = sorted[m];
214
- this.add([midNode.key, midNode.value], midNode.count);
233
+ this.add(midNode.key, midNode.value, midNode.count);
215
234
  stack.push([m + 1, r]);
216
235
  stack.push([l, m - 1]);
217
236
  }
@@ -318,6 +337,24 @@ export class TreeMultimap<V = any, N extends TreeMultimapNode<V, N> = TreeMultim
318
337
  this._count = 0;
319
338
  }
320
339
 
340
+ /**
341
+ * Time complexity: O(n)
342
+ * Space complexity: O(n)
343
+ */
344
+
345
+ /**
346
+ * Time complexity: O(n)
347
+ * Space complexity: O(n)
348
+ *
349
+ * The `clone` function creates a deep copy of a tree object.
350
+ * @returns The `clone()` method is returning a cloned instance of the `TREE` object.
351
+ */
352
+ override clone(): TREE {
353
+ const cloned = this.createTree();
354
+ this.bfs(node => cloned.add(node.key, node.value, node.count));
355
+ return cloned;
356
+ }
357
+
321
358
  /**
322
359
  * Time Complexity: O(1) - constant time, as it performs basic pointer assignments.
323
360
  * Space Complexity: O(1) - constant space, as it only uses a constant amount of memory.
@@ -327,13 +364,13 @@ export class TreeMultimap<V = any, N extends TreeMultimapNode<V, N> = TreeMultim
327
364
  * @param {N | undefined} newNode - The `newNode` parameter represents the node that needs to be
328
365
  * added to the binary tree. It can be of type `N` (which represents a node in the binary tree) or
329
366
  * `undefined` if there is no node to add.
330
- * @param {BTNKey | N | undefined} parent - The `parent` parameter represents the parent node to
367
+ * @param {K | N | undefined} parent - The `parent` parameter represents the parent node to
331
368
  * which the new node will be added as a child. It can be either a node object (`N`) or a key value
332
- * (`BTNKey`).
369
+ * (`K`).
333
370
  * @returns The method `_addTo` returns either the `parent.left` or `parent.right` node that was
334
371
  * added, or `undefined` if no node was added.
335
372
  */
336
- protected override _addTo(newNode: N | undefined, parent: BSTNodeKeyOrNode<N>): N | undefined {
373
+ protected override _addTo(newNode: N | undefined, parent: BSTNodeKeyOrNode<K, N>): N | undefined {
337
374
  parent = this.ensureNode(parent);
338
375
  if (parent) {
339
376
  if (parent.left === undefined) {
@@ -361,14 +398,14 @@ export class TreeMultimap<V = any, N extends TreeMultimapNode<V, N> = TreeMultim
361
398
 
362
399
  /**
363
400
  * The `_swapProperties` function swaps the key, value, count, and height properties between two nodes.
364
- * @param {BTNKey | N | undefined} srcNode - The `srcNode` parameter represents the source node from
365
- * which the values will be swapped. It can be of type `BTNKey`, `N`, or `undefined`.
366
- * @param {BTNKey | N | undefined} destNode - The `destNode` parameter represents the destination
401
+ * @param {K | N | undefined} srcNode - The `srcNode` parameter represents the source node from
402
+ * which the values will be swapped. It can be of type `K`, `N`, or `undefined`.
403
+ * @param {K | N | undefined} destNode - The `destNode` parameter represents the destination
367
404
  * node where the values from the source node will be swapped to.
368
405
  * @returns either the `destNode` object if both `srcNode` and `destNode` are defined, or `undefined`
369
406
  * if either `srcNode` or `destNode` is undefined.
370
407
  */
371
- protected override _swapProperties(srcNode: BSTNodeKeyOrNode<N>, destNode: BSTNodeKeyOrNode<N>): N | undefined {
408
+ protected override _swapProperties(srcNode: BSTNodeKeyOrNode<K, N>, destNode: BSTNodeKeyOrNode<K, N>): N | undefined {
372
409
  srcNode = this.ensureNode(srcNode);
373
410
  destNode = this.ensureNode(destNode);
374
411
  if (srcNode && destNode) {