data-structure-typed 1.37.2 → 1.37.4

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 (42) hide show
  1. package/CHANGELOG.md +3 -1
  2. package/dist/data-structures/binary-tree/avl-tree.d.ts +44 -38
  3. package/dist/data-structures/binary-tree/avl-tree.js +46 -40
  4. package/dist/data-structures/binary-tree/avl-tree.js.map +1 -1
  5. package/dist/data-structures/binary-tree/binary-tree.d.ts +305 -192
  6. package/dist/data-structures/binary-tree/binary-tree.js +304 -201
  7. package/dist/data-structures/binary-tree/binary-tree.js.map +1 -1
  8. package/dist/data-structures/binary-tree/bst.d.ts +111 -64
  9. package/dist/data-structures/binary-tree/bst.js +132 -85
  10. package/dist/data-structures/binary-tree/bst.js.map +1 -1
  11. package/dist/data-structures/binary-tree/tree-multiset.d.ts +49 -41
  12. package/dist/data-structures/binary-tree/tree-multiset.js +49 -41
  13. package/dist/data-structures/binary-tree/tree-multiset.js.map +1 -1
  14. package/dist/types/data-structures/binary-tree.d.ts +2 -2
  15. package/dist/types/data-structures/binary-tree.js +6 -6
  16. package/dist/types/data-structures/binary-tree.js.map +1 -1
  17. package/lib/data-structures/binary-tree/avl-tree.d.ts +44 -38
  18. package/lib/data-structures/binary-tree/avl-tree.js +46 -40
  19. package/lib/data-structures/binary-tree/binary-tree.d.ts +305 -192
  20. package/lib/data-structures/binary-tree/binary-tree.js +305 -202
  21. package/lib/data-structures/binary-tree/bst.d.ts +111 -64
  22. package/lib/data-structures/binary-tree/bst.js +133 -86
  23. package/lib/data-structures/binary-tree/tree-multiset.d.ts +49 -41
  24. package/lib/data-structures/binary-tree/tree-multiset.js +50 -42
  25. package/lib/types/data-structures/binary-tree.d.ts +2 -2
  26. package/lib/types/data-structures/binary-tree.js +5 -5
  27. package/package.json +6 -6
  28. package/src/data-structures/binary-tree/avl-tree.ts +46 -40
  29. package/src/data-structures/binary-tree/binary-tree.ts +328 -207
  30. package/src/data-structures/binary-tree/bst.ts +135 -88
  31. package/src/data-structures/binary-tree/tree-multiset.ts +50 -42
  32. package/src/types/data-structures/binary-tree.ts +2 -2
  33. package/test/config.ts +1 -0
  34. package/test/integration/avl-tree.test.ts +7 -8
  35. package/test/integration/bst.test.ts +17 -16
  36. package/test/unit/data-structures/binary-tree/binary-tree.test.ts +50 -0
  37. package/test/unit/data-structures/binary-tree/bst.test.ts +8 -1
  38. package/test/unit/data-structures/binary-tree/tree-multiset.test.ts +2 -1
  39. package/test/unit/data-structures/linked-list/linked-list.test.ts +1 -1
  40. package/test/utils/big-o.ts +2 -1
  41. package/umd/bundle.min.js +1 -1
  42. package/umd/bundle.min.js.map +1 -1
@@ -15,39 +15,50 @@ import type {
15
15
  MapCallback,
16
16
  MapCallbackReturn
17
17
  } from '../../types';
18
- import {
19
- BinaryTreeDeletedResult,
20
- DFSOrderPattern,
21
- FamilyPosition,
22
- LoopType
23
- } from '../../types';
18
+ import {BinaryTreeDeletedResult, DFSOrderPattern, FamilyPosition, IterationType} from '../../types';
24
19
  import {IBinaryTree} from '../../interfaces';
25
20
  import {trampoline} from '../../utils';
26
21
  import {Queue} from '../queue';
27
22
 
23
+ /**
24
+ * Represents a node in a binary tree.
25
+ * @template V - The type of data stored in the node.
26
+ * @template FAMILY - The type of the family relationship in the binary tree.
27
+ */
28
28
  export class BinaryTreeNode<V = any, FAMILY extends BinaryTreeNode<V, FAMILY> = BinaryTreeNodeNested<V>> {
29
29
  /**
30
- * The constructor function initializes a BinaryTreeNode object with a key and an optional value.
31
- * @param {BinaryTreeNodeKey} key - The `key` parameter is of type `BinaryTreeNodeKey` and represents the unique identifier
32
- * of the binary tree node. It is used to distinguish one node from another in the binary tree.
33
- * @param {V} [val] - The "val" parameter is an optional parameter of type V. It represents the value that will be
34
- * stored in the binary tree node. If no value is provided, it will be set to undefined.
30
+ * Creates a new instance of BinaryTreeNode.
31
+ * @param {BinaryTreeNodeKey} key - The key associated with the node.
32
+ * @param {V} val - The value stored in the node.
35
33
  */
36
34
  constructor(key: BinaryTreeNodeKey, val?: V) {
37
35
  this.key = key;
38
36
  this.val = val;
39
37
  }
40
38
 
39
+ /**
40
+ * The key associated with the node.
41
+ */
41
42
  key: BinaryTreeNodeKey;
42
43
 
44
+ /**
45
+ * The value stored in the node.
46
+ */
43
47
  val: V | undefined;
44
48
 
45
49
  private _left: FAMILY | null | undefined;
46
50
 
51
+ /**
52
+ * Get the left child node.
53
+ */
47
54
  get left(): FAMILY | null | undefined {
48
55
  return this._left;
49
56
  }
50
57
 
58
+ /**
59
+ * Set the left child node.
60
+ * @param {FAMILY | null | undefined} v - The left child node.
61
+ */
51
62
  set left(v: FAMILY | null | undefined) {
52
63
  if (v) {
53
64
  v.parent = this as unknown as FAMILY;
@@ -57,10 +68,17 @@ export class BinaryTreeNode<V = any, FAMILY extends BinaryTreeNode<V, FAMILY> =
57
68
 
58
69
  private _right: FAMILY | null | undefined;
59
70
 
71
+ /**
72
+ * Get the right child node.
73
+ */
60
74
  get right(): FAMILY | null | undefined {
61
75
  return this._right;
62
76
  }
63
77
 
78
+ /**
79
+ * Set the right child node.
80
+ * @param {FAMILY | null | undefined} v - The right child node.
81
+ */
64
82
  set right(v: FAMILY | null | undefined) {
65
83
  if (v) {
66
84
  v.parent = this as unknown as FAMILY;
@@ -68,11 +86,14 @@ export class BinaryTreeNode<V = any, FAMILY extends BinaryTreeNode<V, FAMILY> =
68
86
  this._right = v;
69
87
  }
70
88
 
89
+ /**
90
+ * The parent node of the current node.
91
+ */
71
92
  parent: FAMILY | null | undefined;
72
93
 
73
94
  /**
74
- * The function determines the position of a node in a family tree structure.
75
- * @returns a value of type `FamilyPosition`.
95
+ * Get the position of the node within its family.
96
+ * @returns {FamilyPosition} - The family position of the node.
76
97
  */
77
98
  get familyPosition(): FamilyPosition {
78
99
  const that = this as unknown as FAMILY;
@@ -102,64 +123,75 @@ export class BinaryTreeNode<V = any, FAMILY extends BinaryTreeNode<V, FAMILY> =
102
123
  }
103
124
  }
104
125
 
126
+ /**
127
+ * Represents a binary tree data structure.
128
+ * @template N - The type of the binary tree's nodes.
129
+ */
105
130
  export class BinaryTree<N extends BinaryTreeNode<N['val'], N> = BinaryTreeNode> implements IBinaryTree<N> {
106
131
  /**
107
- * This is a constructor function for a binary tree class that takes an optional options parameter.
108
- * @param {BinaryTreeOptions} [options] - The `options` parameter is an optional object that can be passed to the
109
- * constructor of the `BinaryTree` class. It allows you to customize the behavior of the binary tree by providing
110
- * different configuration options.
132
+ * Creates a new instance of BinaryTree.
133
+ * @param {BinaryTreeOptions} [options] - The options for the binary tree.
111
134
  */
112
135
  constructor(options?: BinaryTreeOptions) {
113
136
  if (options !== undefined) {
114
- const {loopType = LoopType.ITERATIVE} = options;
115
- this._loopType = loopType;
137
+ const { iterationType = IterationType.ITERATIVE } = options;
138
+ this._loopType = iterationType;
116
139
  }
117
140
  }
118
141
 
119
142
  /**
120
- * The function creates a new binary tree node with an optional value.
121
- * @param {BinaryTreeNodeKey} key - The `key` parameter is the identifier for the binary tree node. It is of type
122
- * `BinaryTreeNodeKey`, which represents the unique identifier for each node in the binary tree.
123
- * @param [val] - The `val` parameter is an optional value that can be assigned to the node. It represents the value
124
- * stored in the node.
125
- * @returns a new instance of a BinaryTreeNode with the specified key and value.
143
+ * Creates a new instance of BinaryTreeNode with the given key and value.
144
+ * @param {BinaryTreeNodeKey} key - The key for the new node.
145
+ * @param {N['val']} val - The value for the new node.
146
+ * @returns {N} - The newly created BinaryTreeNode.
126
147
  */
127
148
  createNode(key: BinaryTreeNodeKey, val?: N['val']): N {
128
149
  return new BinaryTreeNode<N['val'], N>(key, val) as N;
129
150
  }
130
151
 
131
- // TODO placeholder node may need redesigned
132
152
  private _root: N | null = null;
133
153
 
154
+ /**
155
+ * Get the root node of the binary tree.
156
+ */
134
157
  get root(): N | null {
135
158
  return this._root;
136
159
  }
137
160
 
138
161
  private _size = 0;
139
162
 
163
+ /**
164
+ * Get the number of nodes in the binary tree.
165
+ */
140
166
  get size(): number {
141
167
  return this._size;
142
168
  }
143
169
 
144
- private _loopType: LoopType = LoopType.ITERATIVE;
170
+ private _loopType: IterationType = IterationType.ITERATIVE;
145
171
 
146
- get loopType(): LoopType {
172
+ /**
173
+ * Get the iteration type used in the binary tree.
174
+ */
175
+ get iterationType(): IterationType {
147
176
  return this._loopType;
148
177
  }
149
178
 
150
- set loopType(v: LoopType) {
179
+ /**
180
+ * Set the iteration type for the binary tree.
181
+ * @param {IterationType} v - The new iteration type to set.
182
+ */
183
+ set iterationType(v: IterationType) {
151
184
  this._loopType = v;
152
185
  }
153
186
 
154
187
  /**
155
- * The `_swap` function swaps the location of two nodes in a binary tree.
156
- * @param {N} srcNode - The source node that you want to _swap with the destination node.
157
- * @param {N} destNode - The `destNode` parameter represents the destination node where the values from `srcNode` will
158
- * be swapped to.
159
- * @returns The `destNode` is being returned.
188
+ * Swap the data of two nodes in the binary tree.
189
+ * @param {N} srcNode - The source node to swap.
190
+ * @param {N} destNode - The destination node to swap.
191
+ * @returns {N} - The destination node after the swap.
160
192
  */
161
193
  protected _swap(srcNode: N, destNode: N): N {
162
- const {key, val} = destNode;
194
+ const { key, val } = destNode;
163
195
  const tempNode = this.createNode(key, val);
164
196
 
165
197
  if (tempNode) {
@@ -174,7 +206,7 @@ export class BinaryTree<N extends BinaryTreeNode<N['val'], N> = BinaryTreeNode>
174
206
  }
175
207
 
176
208
  /**
177
- * The clear() function resets the root, size, and maxKey properties to their initial values.
209
+ * Clear the binary tree, removing all nodes.
178
210
  */
179
211
  clear() {
180
212
  this._root = null;
@@ -182,26 +214,18 @@ export class BinaryTree<N extends BinaryTreeNode<N['val'], N> = BinaryTreeNode>
182
214
  }
183
215
 
184
216
  /**
185
- * The function checks if the size of an object is equal to zero and returns a boolean value.
186
- * @returns A boolean value indicating whether the size of the object is 0 or not.
217
+ * Check if the binary tree is empty.
218
+ * @returns {boolean} - True if the binary tree is empty, false otherwise.
187
219
  */
188
220
  isEmpty(): boolean {
189
221
  return this.size === 0;
190
222
  }
191
223
 
192
224
  /**
193
- * When all leaf nodes are null, it will no longer be possible to add new entity nodes to this binary tree.
194
- * In this scenario, null nodes serve as "sentinel nodes," "virtual nodes," or "placeholder nodes."
195
- */
196
-
197
- /**
198
- * The `add` function adds a new node to a binary tree, either by ID or by creating a new node with a given value.
199
- * @param {BinaryTreeNodeKey | N | null} keyOrNode - The `keyOrNode` parameter can be either a `BinaryTreeNodeKey`, which
200
- * is a number representing the ID of a binary tree node, or it can be a `N` object, which represents a binary tree
201
- * node itself. It can also be `null` if no node is specified.
202
- * @param [val] - The `val` parameter is an optional value that can be assigned to the `val` property of the new node
203
- * being added to the binary tree.
204
- * @returns The function `add` returns either the inserted node (`N`), `null`, or `undefined`.
225
+ * Add a node with the given key and value to the binary tree.
226
+ * @param {BinaryTreeNodeKey | N | null} keyOrNode - The key or node to add to the binary tree.
227
+ * @param {N['val']} val - The value for the new node (optional).
228
+ * @returns {N | null | undefined} - The inserted node, or null if nothing was inserted, or undefined if the operation failed.
205
229
  */
206
230
  add(keyOrNode: BinaryTreeNodeKey | N | null, val?: N['val']): N | null | undefined {
207
231
  const _bfs = (root: N, newNode: N | null): N | undefined | null => {
@@ -257,12 +281,12 @@ export class BinaryTree<N extends BinaryTreeNode<N['val'], N> = BinaryTreeNode>
257
281
  * values, and adds them to the binary tree.
258
282
  * @param {(BinaryTreeNodeKey | null)[] | (N | null)[]} keysOrNodes - An array of BinaryTreeNodeKey or BinaryTreeNode
259
283
  * objects, or null values.
260
- * @param {N['val'][]} [data] - The `data` parameter is an optional array of values (`N['val'][]`) that corresponds to
261
- * the nodes or node IDs being added. It is used to set the value of each node being added. If `data` is not provided,
284
+ * @param {N['val'][]} [values] - The `values` parameter is an optional array of values (`N['val'][]`) that corresponds to
285
+ * the nodes or node IDs being added. It is used to set the value of each node being added. If `values` is not provided,
262
286
  * the value of the nodes will be `undefined`.
263
287
  * @returns The function `addMany` returns an array of `N`, `null`, or `undefined` values.
264
288
  */
265
- addMany(keysOrNodes: (BinaryTreeNodeKey | null)[] | (N | null)[], data?: N['val'][]): (N | null | undefined)[] {
289
+ addMany(keysOrNodes: (BinaryTreeNodeKey | null)[] | (N | null)[], values?: N['val'][]): (N | null | undefined)[] {
266
290
  // TODO not sure addMany not be run multi times
267
291
  const inserted: (N | null | undefined)[] = [];
268
292
 
@@ -278,7 +302,7 @@ export class BinaryTree<N extends BinaryTreeNode<N['val'], N> = BinaryTreeNode>
278
302
  continue;
279
303
  }
280
304
 
281
- const val = data?.[i];
305
+ const val = values?.[i];
282
306
  inserted.push(this.add(keyOrNode, val));
283
307
  }
284
308
  return inserted;
@@ -298,12 +322,14 @@ export class BinaryTree<N extends BinaryTreeNode<N['val'], N> = BinaryTreeNode>
298
322
  return keysOrNodes.length === this.addMany(keysOrNodes, data).length;
299
323
  }
300
324
 
325
+
301
326
  /**
302
- * The `delete` function in TypeScript is used to delete a node from a binary search tree and returns an array of objects
303
- * containing the deleted node and the node that needs to be balanced.
304
- * @param {N | BinaryTreeNodeKey} nodeOrKey - The `nodeOrKey` parameter can be either a node object (`N`) or a binary tree
305
- * node ID (`BinaryTreeNodeKey`).
306
- * @returns The function `delete` returns an array of `BinaryTreeDeletedResult<N>` objects.
327
+ * The `delete` function removes a node from a binary search tree and returns the deleted node along
328
+ * with the parent node that needs to be balanced.
329
+ * @param {N | BinaryTreeNodeKey} nodeOrKey - The `nodeOrKey` parameter can be either a node (`N`) or
330
+ * a key (`BinaryTreeNodeKey`). If it is a key, the function will find the corresponding node in the
331
+ * binary tree.
332
+ * @returns an array of `BinaryTreeDeletedResult<N>` objects.
307
333
  */
308
334
  delete(nodeOrKey: N | BinaryTreeNodeKey): BinaryTreeDeletedResult<N>[] {
309
335
  const bstDeletedResult: BinaryTreeDeletedResult<N>[] = [];
@@ -348,10 +374,16 @@ export class BinaryTree<N extends BinaryTreeNode<N['val'], N> = BinaryTreeNode>
348
374
  }
349
375
 
350
376
  /**
351
- * The function calculates the depth of a node in a binary tree.
352
- * @param {N | BinaryTreeNodeKey | null} distNode - The `distNode` parameter can be any node of the tree
353
- * @param {N | BinaryTreeNodeKey | null} beginRoot - The `beginRoot` parameter can be the predecessor node of distNode
354
- * @returns the depth of the given node or binary tree.
377
+ * The function `getDepth` calculates the depth of a given node in a binary tree relative to a
378
+ * specified root node.
379
+ * @param {N | BinaryTreeNodeKey | null} distNode - The `distNode` parameter represents the node
380
+ * whose depth we want to find in the binary tree. It can be either a node object (`N`), a key value
381
+ * of the node (`BinaryTreeNodeKey`), or `null`.
382
+ * @param {N | BinaryTreeNodeKey | null} beginRoot - The `beginRoot` parameter represents the
383
+ * starting node from which we want to calculate the depth. It can be either a node object or the key
384
+ * of a node in the binary tree. If no value is provided for `beginRoot`, it defaults to the root
385
+ * node of the binary tree.
386
+ * @returns the depth of the `distNode` relative to the `beginRoot`.
355
387
  */
356
388
  getDepth(distNode: N | BinaryTreeNodeKey | null, beginRoot: N | BinaryTreeNodeKey | null = this.root): number {
357
389
  if (typeof distNode === 'number') distNode = this.get(distNode);
@@ -368,17 +400,22 @@ export class BinaryTree<N extends BinaryTreeNode<N['val'], N> = BinaryTreeNode>
368
400
  }
369
401
 
370
402
  /**
371
- * The `getHeight` function calculates the maximum height of a binary tree, either recursively or iteratively.
372
- * @param {N | BinaryTreeNodeKey | null} [beginRoot] - The `beginRoot` parameter is optional and can be of type `N` (a
373
- * generic type representing a node in a binary tree), `BinaryTreeNodeKey` (a type representing the ID of a binary tree
374
- * node), or `null`.
403
+ * The `getHeight` function calculates the maximum height of a binary tree using either recursive or
404
+ * iterative approach.
405
+ * @param {N | BinaryTreeNodeKey | null} beginRoot - The `beginRoot` parameter represents the
406
+ * starting node from which the height of the binary tree is calculated. It can be either a node
407
+ * object (`N`), a key value of a node in the tree (`BinaryTreeNodeKey`), or `null` if no starting
408
+ * node is specified. If `
409
+ * @param iterationType - The `iterationType` parameter is used to determine whether to calculate the
410
+ * height of the binary tree using a recursive approach or an iterative approach. It can have two
411
+ * possible values:
375
412
  * @returns the height of the binary tree.
376
413
  */
377
- getHeight(beginRoot: N | BinaryTreeNodeKey | null = this.root): number {
414
+ getHeight(beginRoot: N | BinaryTreeNodeKey | null = this.root, iterationType = this.iterationType): number {
378
415
  if (typeof beginRoot === 'number') beginRoot = this.get(beginRoot);
379
416
  if (!beginRoot) return -1;
380
417
 
381
- if (this._loopType === LoopType.RECURSIVE) {
418
+ if (iterationType === IterationType.RECURSIVE) {
382
419
  const _getMaxHeight = (cur: N | null | undefined): number => {
383
420
  if (!cur) return -1;
384
421
  const leftHeight = _getMaxHeight(cur.left);
@@ -416,17 +453,19 @@ export class BinaryTree<N extends BinaryTreeNode<N['val'], N> = BinaryTreeNode>
416
453
  protected _defaultCallbackByKey: MapCallback<N> = node => node.key;
417
454
 
418
455
  /**
419
- * The `getMinHeight` function calculates the minimum height of a binary tree using either a recursive or iterative
420
- * approach.
421
- * @param {N | null} [beginRoot] - The `beginRoot` parameter is an optional parameter of type `N` or `null`. It
422
- * represents the starting node from which to calculate the minimum height of a binary tree. If no value is provided
423
- * for `beginRoot`, the `this.root` property is used as the default value.
424
- * @returns The function `getMinHeight` returns the minimum height of the binary tree.
456
+ * The `getMinHeight` function calculates the minimum height of a binary tree using either a
457
+ * recursive or iterative approach.
458
+ * @param {N | null} beginRoot - The `beginRoot` parameter is the starting node from which we want to
459
+ * calculate the minimum height of the tree. It is optional and defaults to the root of the tree if
460
+ * not provided.
461
+ * @param iterationType - The `iterationType` parameter is used to determine the method of iteration
462
+ * to calculate the minimum height of a binary tree. It can have two possible values:
463
+ * @returns The function `getMinHeight` returns the minimum height of a binary tree.
425
464
  */
426
- getMinHeight(beginRoot: N | null = this.root): number {
465
+ getMinHeight(beginRoot: N | null = this.root, iterationType = this.iterationType): number {
427
466
  if (!beginRoot) return -1;
428
467
 
429
- if (this._loopType === LoopType.RECURSIVE) {
468
+ if (iterationType === IterationType.RECURSIVE) {
430
469
  const _getMinHeight = (cur: N | null | undefined): number => {
431
470
  if (!cur) return 0;
432
471
  if (!cur.left && !cur.right) return 0;
@@ -466,10 +505,10 @@ export class BinaryTree<N extends BinaryTreeNode<N['val'], N> = BinaryTreeNode>
466
505
  }
467
506
 
468
507
  /**
469
- * The function checks if a binary tree is perfectly balanced by comparing the minimum height and the height of the
470
- * tree.
471
- * @param {N | null} [beginRoot] - The parameter `beginRoot` is of type `N` or `null`. It represents the root node of a
472
- * tree or null if the tree is empty.
508
+ * The function checks if a binary tree is perfectly balanced by comparing the minimum height and the
509
+ * height of the tree.
510
+ * @param {N | null} beginRoot - The parameter `beginRoot` is of type `N | null`, which means it can
511
+ * either be of type `N` (representing a node in a tree) or `null` (representing an empty tree).
473
512
  * @returns The method is returning a boolean value.
474
513
  */
475
514
  isPerfectlyBalanced(beginRoot: N | null = this.root): boolean {
@@ -477,28 +516,38 @@ export class BinaryTree<N extends BinaryTreeNode<N['val'], N> = BinaryTreeNode>
477
516
  }
478
517
 
479
518
  /**
480
- * The function `getNodes` returns an array of nodes that match a given property name and value in a binary tree.
481
- * @param callback
482
- * @param {BinaryTreeNodeKey | N} nodeProperty - The `nodeProperty` parameter can be either a `BinaryTreeNodeKey` or a
483
- * generic type `N`. It represents the property of the binary tree node that you want to search for.
484
- * specifies the property name to use when searching for nodes. If not provided, it defaults to 'key'.
485
- * @param {boolean} [onlyOne] - The `onlyOne` parameter is an optional boolean parameter that determines whether to
486
- * return only one node that matches the given `nodeProperty` or `propertyName`. If `onlyOne` is set to `true`, the
487
- * function will stop traversing the tree and return the first matching node. If `only
488
- * @param beginRoot
489
- * @returns an array of nodes (type N).
519
+ * The function `getNodes` returns an array of nodes that match a given node property, using either
520
+ * recursive or iterative traversal.
521
+ * @param {BinaryTreeNodeKey | N} nodeProperty - The `nodeProperty` parameter is either a
522
+ * `BinaryTreeNodeKey` or a generic type `N`. It represents the property of the node that we are
523
+ * searching for. It can be a specific key value or any other property of the node.
524
+ * @param callback - The `callback` parameter is a function that takes a node as input and returns a
525
+ * value. This value is compared with the `nodeProperty` parameter to determine if the node should be
526
+ * included in the result. The `callback` parameter has a default value of
527
+ * `this._defaultCallbackByKey`, which
528
+ * @param [onlyOne=false] - A boolean value indicating whether to stop searching after finding the
529
+ * first node that matches the nodeProperty. If set to true, the function will return an array with
530
+ * only one element (or an empty array if no matching node is found). If set to false (default), the
531
+ * function will continue searching for all
532
+ * @param {N | null} beginRoot - The `beginRoot` parameter is the starting node from which the
533
+ * traversal of the binary tree will begin. It is optional and defaults to the root of the binary
534
+ * tree.
535
+ * @param iterationType - The `iterationType` parameter determines the type of iteration used to
536
+ * traverse the binary tree. It can have two possible values:
537
+ * @returns The function `getNodes` returns an array of nodes (`N[]`).
490
538
  */
491
539
  getNodes(
492
540
  nodeProperty: BinaryTreeNodeKey | N,
493
541
  callback: MapCallback<N> = this._defaultCallbackByKey,
494
542
  onlyOne = false,
495
- beginRoot: N | null = this.root
543
+ beginRoot: N | null = this.root,
544
+ iterationType = this.iterationType
496
545
  ): N[] {
497
546
  if (!beginRoot) return [];
498
547
 
499
548
  const ans: N[] = [];
500
549
 
501
- if (this.loopType === LoopType.RECURSIVE) {
550
+ if (iterationType === IterationType.RECURSIVE) {
502
551
  const _traverse = (cur: N) => {
503
552
  if (callback(cur) === nodeProperty) {
504
553
  ans.push(cur);
@@ -529,43 +578,66 @@ export class BinaryTree<N extends BinaryTreeNode<N['val'], N> = BinaryTreeNode>
529
578
  }
530
579
 
531
580
  /**
532
- * The function checks if a binary tree node has a specific property.
533
- * @param callback - The `callback` parameter is a function that takes a node as a parameter and returns a value.
534
- * @param {BinaryTreeNodeKey | N} nodeProperty - The `nodeProperty` parameter can be either a `BinaryTreeNodeKey` or `N`.
535
- * It represents the property of the binary tree node that you want to check.
536
- * specifies the name of the property to be checked in the nodes. If not provided, it defaults to 'key'.
581
+ * The function checks if a binary tree has a node with a given property or key.
582
+ * @param {BinaryTreeNodeKey | N} nodeProperty - The `nodeProperty` parameter is the key or value of
583
+ * the node that you want to find in the binary tree. It can be either a `BinaryTreeNodeKey` or a
584
+ * generic type `N`.
585
+ * @param callback - The `callback` parameter is a function that is used to determine whether a node
586
+ * matches the desired criteria. It takes a node as input and returns a boolean value indicating
587
+ * whether the node matches the criteria or not. The default callback function
588
+ * `this._defaultCallbackByKey` is used if no callback function is
589
+ * @param beginRoot - The `beginRoot` parameter is the starting point for the search. It specifies
590
+ * the node from which the search should begin. By default, it is set to `this.root`, which means the
591
+ * search will start from the root node of the binary tree. However, you can provide a different node
592
+ * as
593
+ * @param iterationType - The `iterationType` parameter specifies the type of iteration to be
594
+ * performed when searching for nodes in the binary tree. It can have one of the following values:
537
595
  * @returns a boolean value.
538
596
  */
539
- has(nodeProperty: BinaryTreeNodeKey | N, callback: MapCallback<N> = this._defaultCallbackByKey): boolean {
597
+ has(
598
+ nodeProperty: BinaryTreeNodeKey | N,
599
+ callback: MapCallback<N> = this._defaultCallbackByKey,
600
+ beginRoot = this.root,
601
+ iterationType = this.iterationType
602
+ ): boolean {
540
603
  // TODO may support finding node by value equal
541
- return this.getNodes(nodeProperty, callback, true).length > 0;
604
+ return this.getNodes(nodeProperty, callback, true, beginRoot, iterationType).length > 0;
542
605
  }
543
606
 
544
607
  /**
545
- * The function returns the first node that matches the given property name and value, or null if no matching node is
546
- * found.
547
- * @param callback - The `callback` parameter is a function that takes a node as a parameter and returns a value.
548
- * @param {BinaryTreeNodeKey | N} nodeProperty - The `nodeProperty` parameter can be either a `BinaryTreeNodeKey` or `N`.
549
- * It represents the property of the binary tree node that you want to search for.
550
- * specifies the property name to be used for searching the binary tree nodes. If this parameter is not provided, the
551
- * default value is set to `'key'`.
552
- * @returns either the value of the specified property of the node, or the node itself if no property name is provided.
553
- * If no matching node is found, it returns null.
608
+ * The function `get` returns the first node in a binary tree that matches the given property or key.
609
+ * @param {BinaryTreeNodeKey | N} nodeProperty - The `nodeProperty` parameter is the key or value of
610
+ * the node that you want to find in the binary tree. It can be either a `BinaryTreeNodeKey` or `N`
611
+ * type.
612
+ * @param callback - The `callback` parameter is a function that is used to determine whether a node
613
+ * matches the desired criteria. It takes a node as input and returns a boolean value indicating
614
+ * whether the node matches the criteria or not. The default callback function
615
+ * (`this._defaultCallbackByKey`) is used if no callback function is
616
+ * @param beginRoot - The `beginRoot` parameter is the starting point for the search. It specifies
617
+ * the root node from which the search should begin.
618
+ * @param iterationType - The `iterationType` parameter specifies the type of iteration to be
619
+ * performed when searching for a node in the binary tree. It can have one of the following values:
620
+ * @returns either the found node (of type N) or null if no node is found.
554
621
  */
555
- get(nodeProperty: BinaryTreeNodeKey | N, callback: MapCallback<N> = this._defaultCallbackByKey): N | null {
622
+ get(
623
+ nodeProperty: BinaryTreeNodeKey | N,
624
+ callback: MapCallback<N> = this._defaultCallbackByKey,
625
+ beginRoot = this.root,
626
+ iterationType = this.iterationType
627
+ ): N | null {
556
628
  // TODO may support finding node by value equal
557
- return this.getNodes(nodeProperty, callback, true)[0] ?? null;
629
+ return this.getNodes(nodeProperty, callback, true, beginRoot, iterationType)[0] ?? null;
558
630
  }
559
631
 
560
632
  /**
561
- * The function `getPathToRoot` returns an array of nodes representing the path from a given node to the root node, with
562
- * an option to reverse the order of the nodes.
563
- * type that represents a node in your specific implementation.
564
- * @param beginRoot - The `beginRoot` parameter is of type `N` and represents the starting node from which you want to
565
- * @param {boolean} [isReverse=true] - The `isReverse` parameter is a boolean flag that determines whether the resulting
566
- * path should be reversed or not. If `isReverse` is set to `true`, the path will be reversed before returning it. If
567
- * `isReverse` is set to `false` or not provided, the path will
568
- * @returns The function `getPathToRoot` returns an array of nodes (`N[]`).
633
+ * The function `getPathToRoot` returns an array of nodes starting from a given node and traversing
634
+ * up to the root node, with the option to reverse the order of the nodes.
635
+ * @param {N} beginRoot - The `beginRoot` parameter represents the starting node from which you want
636
+ * to find the path to the root node.
637
+ * @param [isReverse=true] - The `isReverse` parameter is a boolean flag that determines whether the
638
+ * resulting path should be reversed or not. If `isReverse` is set to `true`, the path will be
639
+ * reversed before returning it. If `isReverse` is set to `false` or not provided, the path will
640
+ * @returns The function `getPathToRoot` returns an array of type `N[]`.
569
641
  */
570
642
  getPathToRoot(beginRoot: N, isReverse = true): N[] {
571
643
  // TODO to support get path through passing key
@@ -581,22 +653,22 @@ export class BinaryTree<N extends BinaryTreeNode<N['val'], N> = BinaryTreeNode>
581
653
  }
582
654
 
583
655
  /**
584
- * The function `getLeftMost` returns the leftmost node in a binary tree, starting from a specified node or the root if
585
- * no node is specified.
586
- * @param {N | BinaryTreeNodeKey | null} [beginRoot] - The `beginRoot` parameter is optional and can be of type `N` (a
587
- * generic type representing a node in a binary tree), `BinaryTreeNodeKey` (a type representing the ID of a binary tree
588
- * node), or `null`.
589
- * @returns The function `getLeftMost` returns the leftmost node in a binary tree. If the `beginRoot` parameter is
590
- * provided, it starts the traversal from that node. If `beginRoot` is not provided or is `null`, it starts the traversal
591
- * from the root of the binary tree. The function returns the leftmost node found during the traversal. If no leftmost
592
- * node is found (
656
+ * The function `getLeftMost` returns the leftmost node in a binary tree, either using recursive or
657
+ * iterative traversal.
658
+ * @param {N | BinaryTreeNodeKey | null} beginRoot - The `beginRoot` parameter is the starting point
659
+ * for finding the leftmost node in a binary tree. It can be either a node object (`N`), a key value
660
+ * of a node (`BinaryTreeNodeKey`), or `null` if the tree is empty.
661
+ * @param iterationType - The `iterationType` parameter is used to determine the type of iteration to
662
+ * be performed when finding the leftmost node in a binary tree. It can have two possible values:
663
+ * @returns The function `getLeftMost` returns the leftmost node (`N`) in a binary tree. If there is
664
+ * no leftmost node, it returns `null`.
593
665
  */
594
- getLeftMost(beginRoot: N | BinaryTreeNodeKey | null = this.root): N | null {
666
+ getLeftMost(beginRoot: N | BinaryTreeNodeKey | null = this.root, iterationType = this.iterationType): N | null {
595
667
  if (typeof beginRoot === 'number') beginRoot = this.get(beginRoot);
596
668
 
597
669
  if (!beginRoot) return beginRoot;
598
670
 
599
- if (this._loopType === LoopType.RECURSIVE) {
671
+ if (iterationType === IterationType.RECURSIVE) {
600
672
  const _traverse = (cur: N): N => {
601
673
  if (!cur.left) return cur;
602
674
  return _traverse(cur.left);
@@ -615,20 +687,21 @@ export class BinaryTree<N extends BinaryTreeNode<N['val'], N> = BinaryTreeNode>
615
687
  }
616
688
 
617
689
  /**
618
- * The `getRightMost` function returns the rightmost node in a binary tree, either recursively or iteratively using tail
619
- * recursion optimization.
620
- * @param {N | null} [beginRoot] - The `node` parameter is an optional parameter of type `N` or `null`. It represents the
621
- * starting node from which we want to find the rightmost node. If no node is provided, the function will default to
622
- * using the root node of the data structure.
623
- * @returns The `getRightMost` function returns the rightmost node in a binary tree. If the `node` parameter is provided,
624
- * it returns the rightmost node starting from that node. If the `node` parameter is not provided, it returns the
625
- * rightmost node starting from the root of the binary tree.
690
+ * The function `getRightMost` returns the rightmost node in a binary tree, either recursively or
691
+ * iteratively.
692
+ * @param {N | null} beginRoot - The `beginRoot` parameter is the starting node from which we want to
693
+ * find the rightmost node. It is of type `N | null`, which means it can either be a node of type `N`
694
+ * or `null`. If it is `null`, it means there is no starting node
695
+ * @param iterationType - The `iterationType` parameter is used to determine the type of iteration to
696
+ * be performed when finding the rightmost node in a binary tree. It can have two possible values:
697
+ * @returns The function `getRightMost` returns the rightmost node (`N`) in a binary tree. If the
698
+ * `beginRoot` parameter is `null`, it returns `null`.
626
699
  */
627
- getRightMost(beginRoot: N | null = this.root): N | null {
700
+ getRightMost(beginRoot: N | null = this.root, iterationType = this.iterationType): N | null {
628
701
  // TODO support get right most by passing key in
629
702
  if (!beginRoot) return beginRoot;
630
703
 
631
- if (this._loopType === LoopType.RECURSIVE) {
704
+ if (iterationType === IterationType.RECURSIVE) {
632
705
  const _traverse = (cur: N): N => {
633
706
  if (!cur.right) return cur;
634
707
  return _traverse(cur.right);
@@ -647,26 +720,30 @@ export class BinaryTree<N extends BinaryTreeNode<N['val'], N> = BinaryTreeNode>
647
720
  }
648
721
 
649
722
  /**
650
- * The function checks if a binary search tree is valid by traversing it either recursively or iteratively.
651
- * @param {N | null} subTreeRoot - The `node` parameter represents the root node of a binary search tree (BST).
652
- * @returns a boolean value.
723
+ * The function `isSubtreeBST` checks if a given binary tree is a valid binary search tree.
724
+ * @param {N} beginRoot - The `beginRoot` parameter is the root node of the binary tree that you want
725
+ * to check if it is a binary search tree (BST) subtree.
726
+ * @param iterationType - The `iterationType` parameter is an optional parameter that specifies the
727
+ * type of iteration to use when checking if a subtree is a binary search tree (BST). It can have two
728
+ * possible values:
729
+ * @returns The function `isSubtreeBST` returns a boolean value.
653
730
  */
654
- isSubtreeBST(subTreeRoot: N | null): boolean {
731
+ isSubtreeBST(beginRoot: N, iterationType = this.iterationType): boolean {
655
732
  // TODO there is a bug
656
- if (!subTreeRoot) return true;
733
+ if (!beginRoot) return true;
657
734
 
658
- if (this._loopType === LoopType.RECURSIVE) {
735
+ if (iterationType === IterationType.RECURSIVE) {
659
736
  const dfs = (cur: N | null | undefined, min: BinaryTreeNodeKey, max: BinaryTreeNodeKey): boolean => {
660
737
  if (!cur) return true;
661
738
  if (cur.key <= min || cur.key >= max) return false;
662
739
  return dfs(cur.left, min, cur.key) && dfs(cur.right, cur.key, max);
663
740
  };
664
741
 
665
- return dfs(subTreeRoot, Number.MIN_SAFE_INTEGER, Number.MAX_SAFE_INTEGER);
742
+ return dfs(beginRoot, Number.MIN_SAFE_INTEGER, Number.MAX_SAFE_INTEGER);
666
743
  } else {
667
744
  const stack = [];
668
745
  let prev = Number.MIN_SAFE_INTEGER,
669
- curr: N | null | undefined = subTreeRoot;
746
+ curr: N | null | undefined = beginRoot;
670
747
  while (curr || stack.length > 0) {
671
748
  while (curr) {
672
749
  stack.push(curr);
@@ -682,40 +759,52 @@ export class BinaryTree<N extends BinaryTreeNode<N['val'], N> = BinaryTreeNode>
682
759
  }
683
760
 
684
761
  /**
685
- * The function isBST checks if the binary tree is valid binary search tree.
686
- * @returns The `isBST()` function is returning a boolean value.
762
+ * The function checks if a binary tree is a binary search tree.
763
+ * @param iterationType - The parameter "iterationType" is used to specify the type of iteration to
764
+ * be used when checking if the binary tree is a binary search tree (BST). It is an optional
765
+ * parameter with a default value of "this.iterationType". The value of "this.iterationType" is not
766
+ * provided in
767
+ * @returns a boolean value.
687
768
  */
688
- isBST(): boolean {
689
- return this.isSubtreeBST(this.root);
769
+ isBST(iterationType = this.iterationType): boolean {
770
+ if (this.root === null) return true;
771
+ return this.isSubtreeBST(this.root, iterationType);
690
772
  }
691
773
 
692
774
  /**
693
- * The function `subTreeTraverse` adds a delta value to a specified property of each node in a subtree.
694
- * @param {N | BinaryTreeNodeKey | null} subTreeRoot - The `subTreeRoot` parameter represents the root node of a binary
695
- * tree or the ID of a node in the binary tree. It can also be `null` if there is no subtree to add to.
696
- * @param callback - The `callback` parameter is a function that takes a node as a parameter and returns a value.
697
- * specifies the property of the binary tree node that should be modified. If not provided, it defaults to 'key'.
698
- * @returns a boolean value.
775
+ * The function `subTreeTraverse` traverses a binary tree and applies a callback function to each
776
+ * node, either recursively or iteratively.
777
+ * @param callback - The `callback` parameter is a function that will be called on each node in the
778
+ * subtree traversal. It takes a single argument, which is the current node being traversed, and
779
+ * returns a value. The return values from each callback invocation will be collected and returned as
780
+ * an array.
781
+ * @param {N | BinaryTreeNodeKey | null} beginRoot - The `beginRoot` parameter is the starting point
782
+ * for traversing the subtree. It can be either a node object, a key value of a node, or `null` to
783
+ * start from the root of the tree.
784
+ * @param iterationType - The `iterationType` parameter determines the type of traversal to be
785
+ * performed on the binary tree. It can have two possible values:
786
+ * @returns The function `subTreeTraverse` returns an array of `MapCallbackReturn<N>`.
699
787
  */
700
788
  subTreeTraverse(
701
789
  callback: MapCallback<N> = this._defaultCallbackByKey,
702
- subTreeRoot: N | BinaryTreeNodeKey | null = this.root
790
+ beginRoot: N | BinaryTreeNodeKey | null = this.root,
791
+ iterationType = this.iterationType
703
792
  ): MapCallbackReturn<N>[] {
704
- if (typeof subTreeRoot === 'number') subTreeRoot = this.get(subTreeRoot);
793
+ if (typeof beginRoot === 'number') beginRoot = this.get(beginRoot);
705
794
 
706
795
  const ans: MapCallbackReturn<N>[] = [];
707
- if (!subTreeRoot) return ans;
796
+ if (!beginRoot) return ans;
708
797
 
709
- if (this._loopType === LoopType.RECURSIVE) {
798
+ if (iterationType === IterationType.RECURSIVE) {
710
799
  const _traverse = (cur: N) => {
711
800
  ans.push(callback(cur));
712
801
  cur.left && _traverse(cur.left);
713
802
  cur.right && _traverse(cur.right);
714
803
  };
715
804
 
716
- _traverse(subTreeRoot);
805
+ _traverse(beginRoot);
717
806
  } else {
718
- const stack: N[] = [subTreeRoot];
807
+ const stack: N[] = [beginRoot];
719
808
 
720
809
  while (stack.length > 0) {
721
810
  const cur = stack.pop()!;
@@ -729,23 +818,29 @@ export class BinaryTree<N extends BinaryTreeNode<N['val'], N> = BinaryTreeNode>
729
818
  }
730
819
 
731
820
  /**
732
- * The dfs function performs a depth-first search traversal on a binary tree and returns the accumulated properties of
733
- * each node based on the specified pattern and property name.
734
- * @param callback
735
- * @param beginRoot - The `beginRoot` parameter is an optional parameter of type `N` or `null`. It represents the
736
- * @param {'in' | 'pre' | 'post'} [pattern] - The traversal pattern: 'in' (in-order), 'pre' (pre-order), or 'post' (post-order).
737
- * @param loopType - The type of loop to use for the depth-first search traversal. The default value is `LoopType.ITERATIVE`.
738
- * @returns an instance of the BinaryTreeNodeProperties class, which contains the accumulated properties of the binary tree nodes based on the specified pattern and node or property name.
821
+ * The `dfs` function performs a depth-first search traversal on a binary tree, executing a callback
822
+ * function on each node according to a specified order pattern.
823
+ * @param callback - The `callback` parameter is a function that will be called on each node during
824
+ * the depth-first search traversal. It takes a node as input and returns a value. The default value
825
+ * is `this._defaultCallbackByKey`, which is a callback function defined elsewhere in the code.
826
+ * @param {DFSOrderPattern} [pattern=in] - The `pattern` parameter determines the order in which the
827
+ * nodes are visited during the depth-first search. There are three possible values for `pattern`:
828
+ * @param {N | null} beginRoot - The `beginRoot` parameter is the starting node for the depth-first
829
+ * search. It determines where the search will begin in the tree or graph structure. If `beginRoot`
830
+ * is `null`, an empty array will be returned.
831
+ * @param {IterationType} iterationType - The `iterationType` parameter determines the type of
832
+ * iteration used in the depth-first search algorithm. It can have two possible values:
833
+ * @returns The function `dfs` returns an array of `MapCallbackReturn<N>` values.
739
834
  */
740
835
  dfs(
741
836
  callback: MapCallback<N> = this._defaultCallbackByKey,
742
837
  pattern: DFSOrderPattern = 'in',
743
838
  beginRoot: N | null = this.root,
744
- loopType: LoopType = LoopType.ITERATIVE
839
+ iterationType: IterationType = IterationType.ITERATIVE
745
840
  ): MapCallbackReturn<N>[] {
746
841
  if (!beginRoot) return [];
747
842
  const ans: MapCallbackReturn<N>[] = [];
748
- if (loopType === LoopType.RECURSIVE) {
843
+ if (iterationType === IterationType.RECURSIVE) {
749
844
  const _traverse = (node: N) => {
750
845
  switch (pattern) {
751
846
  case 'in':
@@ -811,31 +906,42 @@ export class BinaryTree<N extends BinaryTreeNode<N['val'], N> = BinaryTreeNode>
811
906
  // --- start additional methods ---
812
907
 
813
908
  /**
814
- * The `listLevels` function collects nodes from a binary tree by a specified property and organizes them into levels.
815
- * @param {N | null} node - The `node` parameter is a BinaryTreeNode object or null. It represents the root node of a binary tree. If it is null, the function will use the root node of the current binary tree instance.
816
- * @param callback - The `callback` parameter is a function that takes a node and a level as parameters and returns a value.
817
- * @param withLevel - The `withLevel` parameter is a boolean flag that determines whether to include the level of each node in the result. If `withLevel` is set to `true`, the function will include the level of each node in the result. If `withLevel` is set to `false` or not provided, the function will not include the level of each node in the result.
909
+ * The bfs function performs a breadth-first search traversal on a binary tree, executing a callback
910
+ * function on each node.
911
+ * @param callback - The `callback` parameter is a function that will be called for each node in the
912
+ * breadth-first search. It takes a node of type `N` as its argument and returns a value of type
913
+ * `BFSCallbackReturn<N>`. The default value for this parameter is `this._defaultCallbackByKey
914
+ * @param {boolean} [withLevel=false] - The `withLevel` parameter is a boolean flag that determines
915
+ * whether or not to include the level of each node in the callback function. If `withLevel` is set
916
+ * to `true`, the level of each node will be passed as an argument to the callback function. If
917
+ * `withLevel` is
918
+ * @param {N | null} beginRoot - The `beginRoot` parameter is the starting node for the breadth-first
919
+ * search. It determines from which node the search will begin. If `beginRoot` is `null`, the search
920
+ * will not be performed and an empty array will be returned.
921
+ * @param iterationType - The `iterationType` parameter determines the type of iteration to be used
922
+ * in the breadth-first search (BFS) algorithm. It can have two possible values:
923
+ * @returns The function `bfs` returns an array of `BFSCallbackReturn<N>[]`.
818
924
  */
819
925
  bfs(
820
926
  callback: BFSCallback<N> = this._defaultCallbackByKey,
821
927
  withLevel: boolean = false,
822
- node?: N | null
928
+ beginRoot: N | null = this.root,
929
+ iterationType = this.iterationType
823
930
  ): BFSCallbackReturn<N>[] {
824
- if (!node) node = this.root;
825
- if (!node) return [];
931
+ if (!beginRoot) return [];
826
932
 
827
933
  const ans: BFSCallbackReturn<N>[] = [];
828
934
 
829
- if (this.loopType === LoopType.RECURSIVE) {
935
+ if (iterationType === IterationType.RECURSIVE) {
830
936
  const _recursive = (node: N, level: number) => {
831
937
  callback && ans.push(callback(node, withLevel ? level : undefined));
832
938
  if (node.left) _recursive(node.left, level + 1);
833
939
  if (node.right) _recursive(node.right, level + 1);
834
940
  };
835
941
 
836
- _recursive(node, 0);
942
+ _recursive(beginRoot, 0);
837
943
  } else {
838
- const stack: [N, number][] = [[node, 0]];
944
+ const stack: [N, number][] = [[beginRoot, 0]];
839
945
 
840
946
  while (stack.length > 0) {
841
947
  const head = stack.pop()!;
@@ -850,9 +956,9 @@ export class BinaryTree<N extends BinaryTreeNode<N['val'], N> = BinaryTreeNode>
850
956
  }
851
957
 
852
958
  /**
853
- * The function returns the predecessor of a given node in a binary tree.
854
- * @param node - The parameter `node` is a BinaryTreeNode object, representing a node in a binary tree.
855
- * @returns the predecessor of the given node in a binary tree.
959
+ * The function returns the predecessor node of a given node in a binary tree.
960
+ * @param {N} node - The parameter "node" represents a node in a binary tree.
961
+ * @returns The function `getPredecessor` returns the predecessor node of the given node `node`.
856
962
  */
857
963
  getPredecessor(node: N): N {
858
964
  if (node.left) {
@@ -871,22 +977,34 @@ export class BinaryTree<N extends BinaryTreeNode<N['val'], N> = BinaryTreeNode>
871
977
  /**
872
978
  * Time complexity is O(n)
873
979
  * Space complexity of Iterative dfs equals to recursive dfs which is O(n) because of the stack
980
+ * The Morris algorithm only modifies the tree's structure during traversal; once the traversal is complete,
981
+ * the tree's structure should be restored to its original state to maintain the tree's integrity.
982
+ * This is because the purpose of the Morris algorithm is to save space rather than permanently alter the tree's shape.
874
983
  */
875
984
 
876
985
  /**
877
- * The `morris` function performs an in-order, pre-order, or post-order traversal on a binary tree using the Morris traversal algorithm.
878
- * @param {'in' | 'pre' | 'post'} [pattern] - The traversal pattern: 'in' (in-order), 'pre' (pre-order), or 'post' (post-order).
879
- * @param callback - The `callback` parameter is a function that takes a node as a parameter and returns a value.
880
- * @returns An array of BinaryTreeNodeProperties<N> objects.
986
+ * The `morris` function performs a depth-first traversal of a binary tree using the Morris traversal
987
+ * algorithm and returns an array of values obtained by applying a callback function to each node.
988
+ * @param callback - The `callback` parameter is a function that will be called on each node in the
989
+ * tree. It takes a node of type `N` as input and returns a value of type `MapCallbackReturn<N>`. The
990
+ * default value for this parameter is `this._defaultCallbackByKey`.
991
+ * @param {DFSOrderPattern} [pattern=in] - The `pattern` parameter in the `morris` function
992
+ * determines the order in which the nodes of a binary tree are traversed. It can have one of the
993
+ * following values:
994
+ * @param {N | null} beginRoot - The `beginRoot` parameter is the starting node for the Morris
995
+ * traversal. It specifies the root node of the tree from which the traversal should begin. If
996
+ * `beginRoot` is `null`, an empty array will be returned.
997
+ * @returns The `morris` function returns an array of `MapCallbackReturn<N>` values.
881
998
  */
882
999
  morris(
883
1000
  callback: MapCallback<N> = this._defaultCallbackByKey,
884
- pattern: DFSOrderPattern = 'in'
1001
+ pattern: DFSOrderPattern = 'in',
1002
+ beginRoot: N | null = this.root
885
1003
  ): MapCallbackReturn<N>[] {
886
- if (this.root === null) return [];
1004
+ if (beginRoot === null) return [];
887
1005
  const ans: MapCallbackReturn<N>[] = [];
888
1006
 
889
- let cur: N | null | undefined = this.root;
1007
+ let cur: N | null | undefined = beginRoot;
890
1008
  const _reverseEdge = (node: N | null | undefined) => {
891
1009
  let pre: N | null | undefined = null;
892
1010
  let next: N | null | undefined = null;
@@ -957,21 +1075,22 @@ export class BinaryTree<N extends BinaryTreeNode<N['val'], N> = BinaryTreeNode>
957
1075
  }
958
1076
  cur = cur.right;
959
1077
  }
960
- _printEdge(this.root);
1078
+ _printEdge(beginRoot);
961
1079
  break;
962
1080
  }
963
1081
  return ans;
964
1082
  }
965
1083
 
966
1084
  /**
967
- * The function adds a new node to a binary tree if there is an available position.
968
- * @param {N | null} newNode - The `newNode` parameter is of type `N | null`, which means it can either be a node of
969
- * type `N` or `null`. It represents the node that you want to add to the binary tree.
970
- * @param {N} parent - The parent parameter is of type N, which represents a node in a binary tree.
971
- * @returns either the left or right child node of the parent node, depending on which child is available for adding
972
- * the new node. If a new node is added, the function also updates the size of the binary tree. If neither the left nor
973
- * right child is available, the function returns undefined. If the parent node is null, the function also returns
974
- * undefined.
1085
+ * The function `_addTo` adds a new node to a binary tree if there is an available position.
1086
+ * @param {N | null} newNode - The `newNode` parameter represents the node that you want to add to
1087
+ * the binary tree. It can be either a node object or `null`.
1088
+ * @param {N} parent - The `parent` parameter represents the parent node to which the new node will
1089
+ * be added as a child.
1090
+ * @returns either the left or right child node of the parent node, depending on which child is
1091
+ * available for adding the new node. If a new node is added, the function also updates the size of
1092
+ * the binary tree. If neither the left nor right child is available, the function returns undefined.
1093
+ * If the parent node is null, the function also returns undefined.
975
1094
  */
976
1095
  protected _addTo(newNode: N | null, parent: N): N | null | undefined {
977
1096
  if (parent) {
@@ -998,9 +1117,10 @@ export class BinaryTree<N extends BinaryTreeNode<N['val'], N> = BinaryTreeNode>
998
1117
  }
999
1118
 
1000
1119
  /**
1001
- * The function sets the root property of an object to a given value, and if the value is not null, it also sets the
1002
- * parent property of the value to undefined.
1003
- * @param {N | null} v - The parameter `v` is of type `N | null`, which means it can either be of type `N` or `null`.
1120
+ * The function sets the root property of an object to a given value, and if the value is not null,
1121
+ * it also sets the parent property of the value to undefined.
1122
+ * @param {N | null} v - The parameter `v` is of type `N | null`, which means it can either be of
1123
+ * type `N` or `null`.
1004
1124
  */
1005
1125
  protected _setRoot(v: N | null) {
1006
1126
  if (v) {
@@ -1010,8 +1130,9 @@ export class BinaryTree<N extends BinaryTreeNode<N['val'], N> = BinaryTreeNode>
1010
1130
  }
1011
1131
 
1012
1132
  /**
1013
- * The function sets the size of a protected variable.
1014
- * @param {number} v - number
1133
+ * The function sets the value of the protected property "_size" to the given number.
1134
+ * @param {number} v - The parameter "v" is a number that represents the size value that we want to
1135
+ * set.
1015
1136
  */
1016
1137
  protected _setSize(v: number) {
1017
1138
  this._size = v;