linked-list-typed 2.4.5 → 2.5.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 (76) hide show
  1. package/README.md +14 -50
  2. package/dist/cjs/index.cjs +1538 -294
  3. package/dist/cjs/index.cjs.map +1 -1
  4. package/dist/cjs-legacy/index.cjs +1544 -291
  5. package/dist/cjs-legacy/index.cjs.map +1 -1
  6. package/dist/esm/index.mjs +1538 -294
  7. package/dist/esm/index.mjs.map +1 -1
  8. package/dist/esm-legacy/index.mjs +1544 -291
  9. package/dist/esm-legacy/index.mjs.map +1 -1
  10. package/dist/types/data-structures/base/iterable-element-base.d.ts +1 -1
  11. package/dist/types/data-structures/binary-tree/avl-tree.d.ts +128 -51
  12. package/dist/types/data-structures/binary-tree/binary-indexed-tree.d.ts +210 -164
  13. package/dist/types/data-structures/binary-tree/binary-tree.d.ts +429 -78
  14. package/dist/types/data-structures/binary-tree/bst.d.ts +311 -28
  15. package/dist/types/data-structures/binary-tree/red-black-tree.d.ts +212 -32
  16. package/dist/types/data-structures/binary-tree/segment-tree.d.ts +218 -152
  17. package/dist/types/data-structures/binary-tree/tree-map.d.ts +1281 -5
  18. package/dist/types/data-structures/binary-tree/tree-multi-map.d.ts +1087 -201
  19. package/dist/types/data-structures/binary-tree/tree-multi-set.d.ts +858 -65
  20. package/dist/types/data-structures/binary-tree/tree-set.d.ts +1133 -5
  21. package/dist/types/data-structures/graph/directed-graph.d.ts +219 -47
  22. package/dist/types/data-structures/graph/map-graph.d.ts +59 -1
  23. package/dist/types/data-structures/graph/undirected-graph.d.ts +204 -59
  24. package/dist/types/data-structures/hash/hash-map.d.ts +230 -77
  25. package/dist/types/data-structures/heap/heap.d.ts +287 -99
  26. package/dist/types/data-structures/heap/max-heap.d.ts +46 -0
  27. package/dist/types/data-structures/heap/min-heap.d.ts +59 -0
  28. package/dist/types/data-structures/linked-list/doubly-linked-list.d.ts +286 -44
  29. package/dist/types/data-structures/linked-list/singly-linked-list.d.ts +278 -65
  30. package/dist/types/data-structures/linked-list/skip-linked-list.d.ts +415 -12
  31. package/dist/types/data-structures/matrix/matrix.d.ts +331 -0
  32. package/dist/types/data-structures/priority-queue/max-priority-queue.d.ts +57 -0
  33. package/dist/types/data-structures/priority-queue/min-priority-queue.d.ts +60 -0
  34. package/dist/types/data-structures/priority-queue/priority-queue.d.ts +60 -0
  35. package/dist/types/data-structures/queue/deque.d.ts +272 -65
  36. package/dist/types/data-structures/queue/queue.d.ts +211 -42
  37. package/dist/types/data-structures/stack/stack.d.ts +174 -32
  38. package/dist/types/data-structures/trie/trie.d.ts +213 -43
  39. package/dist/types/types/data-structures/binary-tree/segment-tree.d.ts +1 -1
  40. package/dist/types/types/data-structures/linked-list/skip-linked-list.d.ts +1 -4
  41. package/dist/umd/linked-list-typed.js +1541 -289
  42. package/dist/umd/linked-list-typed.js.map +1 -1
  43. package/dist/umd/linked-list-typed.min.js +1 -1
  44. package/dist/umd/linked-list-typed.min.js.map +1 -1
  45. package/package.json +2 -2
  46. package/src/data-structures/base/iterable-element-base.ts +4 -5
  47. package/src/data-structures/binary-tree/avl-tree.ts +134 -51
  48. package/src/data-structures/binary-tree/binary-indexed-tree.ts +302 -247
  49. package/src/data-structures/binary-tree/binary-tree.ts +429 -79
  50. package/src/data-structures/binary-tree/bst.ts +335 -34
  51. package/src/data-structures/binary-tree/red-black-tree.ts +290 -97
  52. package/src/data-structures/binary-tree/segment-tree.ts +372 -248
  53. package/src/data-structures/binary-tree/tree-map.ts +1284 -6
  54. package/src/data-structures/binary-tree/tree-multi-map.ts +1094 -211
  55. package/src/data-structures/binary-tree/tree-multi-set.ts +858 -65
  56. package/src/data-structures/binary-tree/tree-set.ts +1136 -9
  57. package/src/data-structures/graph/directed-graph.ts +219 -47
  58. package/src/data-structures/graph/map-graph.ts +59 -1
  59. package/src/data-structures/graph/undirected-graph.ts +204 -59
  60. package/src/data-structures/hash/hash-map.ts +230 -77
  61. package/src/data-structures/heap/heap.ts +287 -99
  62. package/src/data-structures/heap/max-heap.ts +46 -0
  63. package/src/data-structures/heap/min-heap.ts +59 -0
  64. package/src/data-structures/linked-list/doubly-linked-list.ts +286 -44
  65. package/src/data-structures/linked-list/singly-linked-list.ts +278 -65
  66. package/src/data-structures/linked-list/skip-linked-list.ts +689 -90
  67. package/src/data-structures/matrix/matrix.ts +416 -12
  68. package/src/data-structures/priority-queue/max-priority-queue.ts +57 -0
  69. package/src/data-structures/priority-queue/min-priority-queue.ts +60 -0
  70. package/src/data-structures/priority-queue/priority-queue.ts +60 -0
  71. package/src/data-structures/queue/deque.ts +272 -65
  72. package/src/data-structures/queue/queue.ts +211 -42
  73. package/src/data-structures/stack/stack.ts +174 -32
  74. package/src/data-structures/trie/trie.ts +213 -43
  75. package/src/types/data-structures/binary-tree/segment-tree.ts +1 -1
  76. package/src/types/data-structures/linked-list/skip-linked-list.ts +2 -1
@@ -1,55 +1,14 @@
1
1
  var __defProp = Object.defineProperty;
2
+ var __typeError = (msg) => {
3
+ throw TypeError(msg);
4
+ };
2
5
  var __defNormalProp = (obj, key, value) => key in obj ? __defProp(obj, key, { enumerable: true, configurable: true, writable: true, value }) : obj[key] = value;
3
6
  var __name = (target, value) => __defProp(target, "name", { value, configurable: true });
4
7
  var __publicField = (obj, key, value) => __defNormalProp(obj, typeof key !== "symbol" ? key + "" : key, value);
5
-
6
- // src/common/error.ts
7
- var ERR = {
8
- // Range / index
9
- indexOutOfRange: /* @__PURE__ */ __name((index, min, max, ctx) => `${ctx ? ctx + ": " : ""}Index ${index} is out of range [${min}, ${max}].`, "indexOutOfRange"),
10
- invalidIndex: /* @__PURE__ */ __name((ctx) => `${ctx ? ctx + ": " : ""}Index must be an integer.`, "invalidIndex"),
11
- // Type / argument
12
- invalidArgument: /* @__PURE__ */ __name((reason, ctx) => `${ctx ? ctx + ": " : ""}${reason}`, "invalidArgument"),
13
- comparatorRequired: /* @__PURE__ */ __name((ctx) => `${ctx ? ctx + ": " : ""}Comparator is required for non-number/non-string/non-Date keys.`, "comparatorRequired"),
14
- invalidKey: /* @__PURE__ */ __name((reason, ctx) => `${ctx ? ctx + ": " : ""}${reason}`, "invalidKey"),
15
- notAFunction: /* @__PURE__ */ __name((name, ctx) => `${ctx ? ctx + ": " : ""}${name} must be a function.`, "notAFunction"),
16
- invalidEntry: /* @__PURE__ */ __name((ctx) => `${ctx ? ctx + ": " : ""}Each entry must be a [key, value] tuple.`, "invalidEntry"),
17
- invalidNaN: /* @__PURE__ */ __name((ctx) => `${ctx ? ctx + ": " : ""}NaN is not a valid key.`, "invalidNaN"),
18
- invalidDate: /* @__PURE__ */ __name((ctx) => `${ctx ? ctx + ": " : ""}Invalid Date key.`, "invalidDate"),
19
- reduceEmpty: /* @__PURE__ */ __name((ctx) => `${ctx ? ctx + ": " : ""}Reduce of empty structure with no initial value.`, "reduceEmpty"),
20
- callbackReturnType: /* @__PURE__ */ __name((expected, got, ctx) => `${ctx ? ctx + ": " : ""}Callback must return ${expected}; got ${got}.`, "callbackReturnType"),
21
- // State / operation
22
- invalidOperation: /* @__PURE__ */ __name((reason, ctx) => `${ctx ? ctx + ": " : ""}${reason}`, "invalidOperation"),
23
- // Matrix
24
- matrixDimensionMismatch: /* @__PURE__ */ __name((op) => `Matrix: Dimensions must be compatible for ${op}.`, "matrixDimensionMismatch"),
25
- matrixSingular: /* @__PURE__ */ __name(() => "Matrix: Singular matrix, inverse does not exist.", "matrixSingular"),
26
- matrixNotSquare: /* @__PURE__ */ __name(() => "Matrix: Must be square for inversion.", "matrixNotSquare"),
27
- matrixNotRectangular: /* @__PURE__ */ __name(() => "Matrix: Must be rectangular for transposition.", "matrixNotRectangular"),
28
- matrixRowMismatch: /* @__PURE__ */ __name((expected, got) => `Matrix: Expected row length ${expected}, but got ${got}.`, "matrixRowMismatch")
29
- };
30
-
31
- // src/common/index.ts
32
- var DFSOperation = /* @__PURE__ */ ((DFSOperation2) => {
33
- DFSOperation2[DFSOperation2["VISIT"] = 0] = "VISIT";
34
- DFSOperation2[DFSOperation2["PROCESS"] = 1] = "PROCESS";
35
- return DFSOperation2;
36
- })(DFSOperation || {});
37
- var _Range = class _Range {
38
- constructor(low, high, includeLow = true, includeHigh = true) {
39
- this.low = low;
40
- this.high = high;
41
- this.includeLow = includeLow;
42
- this.includeHigh = includeHigh;
43
- }
44
- // Determine whether a key is within the range
45
- isInRange(key, comparator) {
46
- const lowCheck = this.includeLow ? comparator(key, this.low) >= 0 : comparator(key, this.low) > 0;
47
- const highCheck = this.includeHigh ? comparator(key, this.high) <= 0 : comparator(key, this.high) < 0;
48
- return lowCheck && highCheck;
49
- }
50
- };
51
- __name(_Range, "Range");
52
- var Range = _Range;
8
+ var __accessCheck = (obj, member, msg) => member.has(obj) || __typeError("Cannot " + msg);
9
+ var __privateGet = (obj, member, getter) => (__accessCheck(obj, member, "read from private field"), getter ? getter.call(obj) : member.get(obj));
10
+ var __privateAdd = (obj, member, value) => member.has(obj) ? __typeError("Cannot add the same private member more than once") : member instanceof WeakSet ? member.add(obj) : member.set(obj, value);
11
+ var __privateSet = (obj, member, value, setter) => (__accessCheck(obj, member, "write to private field"), member.set(obj, value), value);
53
12
 
54
13
  // src/data-structures/base/iterable-element-base.ts
55
14
  var _IterableElementBase = class _IterableElementBase {
@@ -73,7 +32,7 @@ var _IterableElementBase = class _IterableElementBase {
73
32
  if (options) {
74
33
  const { toElementFn } = options;
75
34
  if (typeof toElementFn === "function") this._toElementFn = toElementFn;
76
- else if (toElementFn) throw new TypeError(ERR.notAFunction("toElementFn"));
35
+ else if (toElementFn) throw new TypeError("toElementFn must be a function type");
77
36
  }
78
37
  }
79
38
  /**
@@ -229,7 +188,7 @@ var _IterableElementBase = class _IterableElementBase {
229
188
  acc = initialValue;
230
189
  } else {
231
190
  const first = iter.next();
232
- if (first.done) throw new TypeError(ERR.reduceEmpty());
191
+ if (first.done) throw new TypeError("Reduce of empty structure with no initial value");
233
192
  acc = first.value;
234
193
  index = 1;
235
194
  }
@@ -767,11 +726,37 @@ var _SinglyLinkedList = class _SinglyLinkedList extends LinearLinkedBase {
767
726
  return list;
768
727
  }
769
728
  /**
770
- * Append an element/node to the tail.
771
- * @remarks Time O(1), Space O(1)
772
- * @param elementOrNode - Element or node to append.
773
- * @returns True when appended.
774
- */
729
+ * Append an element/node to the tail.
730
+ * @remarks Time O(1), Space O(1)
731
+ * @param elementOrNode - Element or node to append.
732
+ * @returns True when appended.
733
+
734
+
735
+
736
+
737
+
738
+
739
+
740
+
741
+
742
+
743
+
744
+ * @example
745
+ * // basic SinglyLinkedList creation and push operation
746
+ * // Create a simple SinglyLinkedList with initial values
747
+ * const list = new SinglyLinkedList([1, 2, 3, 4, 5]);
748
+ *
749
+ * // Verify the list maintains insertion order
750
+ * console.log([...list]); // [1, 2, 3, 4, 5];
751
+ *
752
+ * // Check length
753
+ * console.log(list.length); // 5;
754
+ *
755
+ * // Push a new element to the end
756
+ * list.push(6);
757
+ * console.log(list.length); // 6;
758
+ * console.log([...list]); // [1, 2, 3, 4, 5, 6];
759
+ */
775
760
  push(elementOrNode) {
776
761
  const newNode = this._ensureNode(elementOrNode);
777
762
  if (!this.head) {
@@ -785,10 +770,36 @@ var _SinglyLinkedList = class _SinglyLinkedList extends LinearLinkedBase {
785
770
  return true;
786
771
  }
787
772
  /**
788
- * Remove and return the tail element.
789
- * @remarks Time O(N), Space O(1)
790
- * @returns Removed element or undefined.
791
- */
773
+ * Remove and return the tail element.
774
+ * @remarks Time O(N), Space O(1)
775
+ * @returns Removed element or undefined.
776
+
777
+
778
+
779
+
780
+
781
+
782
+
783
+
784
+
785
+
786
+
787
+ * @example
788
+ * // SinglyLinkedList pop and shift operations
789
+ * const list = new SinglyLinkedList<number>([10, 20, 30, 40, 50]);
790
+ *
791
+ * // Pop removes from the end
792
+ * const last = list.pop();
793
+ * console.log(last); // 50;
794
+ *
795
+ * // Shift removes from the beginning
796
+ * const first = list.shift();
797
+ * console.log(first); // 10;
798
+ *
799
+ * // Verify remaining elements
800
+ * console.log([...list]); // [20, 30, 40];
801
+ * console.log(list.length); // 3;
802
+ */
792
803
  pop() {
793
804
  var _a;
794
805
  if (!this.head) return void 0;
@@ -808,10 +819,26 @@ var _SinglyLinkedList = class _SinglyLinkedList extends LinearLinkedBase {
808
819
  return value;
809
820
  }
810
821
  /**
811
- * Remove and return the head element.
812
- * @remarks Time O(1), Space O(1)
813
- * @returns Removed element or undefined.
814
- */
822
+ * Remove and return the head element.
823
+ * @remarks Time O(1), Space O(1)
824
+ * @returns Removed element or undefined.
825
+
826
+
827
+
828
+
829
+
830
+
831
+
832
+
833
+
834
+
835
+
836
+ * @example
837
+ * // Remove from the front
838
+ * const list = new SinglyLinkedList<number>([10, 20, 30]);
839
+ * console.log(list.shift()); // 10;
840
+ * console.log(list.length); // 2;
841
+ */
815
842
  shift() {
816
843
  if (!this.head) return void 0;
817
844
  const removed = this.head;
@@ -821,11 +848,42 @@ var _SinglyLinkedList = class _SinglyLinkedList extends LinearLinkedBase {
821
848
  return removed.value;
822
849
  }
823
850
  /**
824
- * Prepend an element/node to the head.
825
- * @remarks Time O(1), Space O(1)
826
- * @param elementOrNode - Element or node to prepend.
827
- * @returns True when prepended.
828
- */
851
+ * Prepend an element/node to the head.
852
+ * @remarks Time O(1), Space O(1)
853
+ * @param elementOrNode - Element or node to prepend.
854
+ * @returns True when prepended.
855
+
856
+
857
+
858
+
859
+
860
+
861
+
862
+
863
+
864
+
865
+
866
+ * @example
867
+ * // SinglyLinkedList unshift and forward traversal
868
+ * const list = new SinglyLinkedList<number>([20, 30, 40]);
869
+ *
870
+ * // Unshift adds to the beginning
871
+ * list.unshift(10);
872
+ * console.log([...list]); // [10, 20, 30, 40];
873
+ *
874
+ * // Access elements (forward traversal only for singly linked)
875
+ * const second = list.at(1);
876
+ * console.log(second); // 20;
877
+ *
878
+ * // SinglyLinkedList allows forward iteration only
879
+ * const elements: number[] = [];
880
+ * for (const item of list) {
881
+ * elements.push(item);
882
+ * }
883
+ * console.log(elements); // [10, 20, 30, 40];
884
+ *
885
+ * console.log(list.length); // 4;
886
+ */
829
887
  unshift(elementOrNode) {
830
888
  const newNode = this._ensureNode(elementOrNode);
831
889
  if (!this.head) {
@@ -881,11 +939,28 @@ var _SinglyLinkedList = class _SinglyLinkedList extends LinearLinkedBase {
881
939
  return void 0;
882
940
  }
883
941
  /**
884
- * Get the element at a given index.
885
- * @remarks Time O(N), Space O(1)
886
- * @param index - Zero-based index.
887
- * @returns Element or undefined.
888
- */
942
+ * Get the element at a given index.
943
+ * @remarks Time O(N), Space O(1)
944
+ * @param index - Zero-based index.
945
+ * @returns Element or undefined.
946
+
947
+
948
+
949
+
950
+
951
+
952
+
953
+
954
+
955
+
956
+
957
+ * @example
958
+ * // Access element by index
959
+ * const list = new SinglyLinkedList<string>(['a', 'b', 'c', 'd']);
960
+ * console.log(list.at(0)); // 'a';
961
+ * console.log(list.at(2)); // 'c';
962
+ * console.log(list.at(3)); // 'd';
963
+ */
889
964
  at(index) {
890
965
  if (index < 0 || index >= this._length) return void 0;
891
966
  let current = this.head;
@@ -902,11 +977,23 @@ var _SinglyLinkedList = class _SinglyLinkedList extends LinearLinkedBase {
902
977
  return elementNodeOrPredicate instanceof SinglyLinkedListNode;
903
978
  }
904
979
  /**
905
- * Get the node reference at a given index.
906
- * @remarks Time O(N), Space O(1)
907
- * @param index - Zero-based index.
908
- * @returns Node or undefined.
909
- */
980
+ * Get the node reference at a given index.
981
+ * @remarks Time O(N), Space O(1)
982
+ * @param index - Zero-based index.
983
+ * @returns Node or undefined.
984
+
985
+
986
+
987
+
988
+
989
+
990
+
991
+
992
+ * @example
993
+ * // Get node at index
994
+ * const list = new SinglyLinkedList<string>(['a', 'b', 'c']);
995
+ * console.log(list.getNodeAt(1)?.value); // 'b';
996
+ */
910
997
  getNodeAt(index) {
911
998
  if (index < 0 || index >= this._length) return void 0;
912
999
  let current = this.head;
@@ -914,11 +1001,24 @@ var _SinglyLinkedList = class _SinglyLinkedList extends LinearLinkedBase {
914
1001
  return current;
915
1002
  }
916
1003
  /**
917
- * Delete the element at an index.
918
- * @remarks Time O(N), Space O(1)
919
- * @param index - Zero-based index.
920
- * @returns Removed element or undefined.
921
- */
1004
+ * Delete the element at an index.
1005
+ * @remarks Time O(N), Space O(1)
1006
+ * @param index - Zero-based index.
1007
+ * @returns Removed element or undefined.
1008
+
1009
+
1010
+
1011
+
1012
+
1013
+
1014
+
1015
+
1016
+ * @example
1017
+ * // Remove by index
1018
+ * const list = new SinglyLinkedList<string>(['a', 'b', 'c']);
1019
+ * list.deleteAt(1);
1020
+ * console.log(list.toArray()); // ['a', 'c'];
1021
+ */
922
1022
  deleteAt(index) {
923
1023
  if (index < 0 || index >= this._length) return void 0;
924
1024
  if (index === 0) return this.shift();
@@ -931,11 +1031,24 @@ var _SinglyLinkedList = class _SinglyLinkedList extends LinearLinkedBase {
931
1031
  return value;
932
1032
  }
933
1033
  /**
934
- * Delete the first match by value/node.
935
- * @remarks Time O(N), Space O(1)
936
- * @param [elementOrNode] - Element or node to remove; if omitted/undefined, nothing happens.
937
- * @returns True if removed.
938
- */
1034
+ * Delete the first match by value/node.
1035
+ * @remarks Time O(N), Space O(1)
1036
+ * @param [elementOrNode] - Element or node to remove; if omitted/undefined, nothing happens.
1037
+ * @returns True if removed.
1038
+
1039
+
1040
+
1041
+
1042
+
1043
+
1044
+
1045
+
1046
+ * @example
1047
+ * // Remove first occurrence
1048
+ * const list = new SinglyLinkedList<number>([1, 2, 3, 2]);
1049
+ * list.delete(2);
1050
+ * console.log(list.toArray()); // [1, 3, 2];
1051
+ */
939
1052
  delete(elementOrNode) {
940
1053
  if (elementOrNode === void 0 || !this.head) return false;
941
1054
  const node = this.isNode(elementOrNode) ? elementOrNode : this.getNode(elementOrNode);
@@ -952,12 +1065,25 @@ var _SinglyLinkedList = class _SinglyLinkedList extends LinearLinkedBase {
952
1065
  return true;
953
1066
  }
954
1067
  /**
955
- * Insert a new element/node at an index, shifting following nodes.
956
- * @remarks Time O(N), Space O(1)
957
- * @param index - Zero-based index.
958
- * @param newElementOrNode - Element or node to insert.
959
- * @returns True if inserted.
960
- */
1068
+ * Insert a new element/node at an index, shifting following nodes.
1069
+ * @remarks Time O(N), Space O(1)
1070
+ * @param index - Zero-based index.
1071
+ * @param newElementOrNode - Element or node to insert.
1072
+ * @returns True if inserted.
1073
+
1074
+
1075
+
1076
+
1077
+
1078
+
1079
+
1080
+
1081
+ * @example
1082
+ * // Insert at index
1083
+ * const list = new SinglyLinkedList<number>([1, 3]);
1084
+ * list.addAt(1, 2);
1085
+ * console.log(list.toArray()); // [1, 2, 3];
1086
+ */
961
1087
  addAt(index, newElementOrNode) {
962
1088
  if (index < 0 || index > this._length) return false;
963
1089
  if (index === 0) return this.unshift(newElementOrNode);
@@ -983,28 +1109,70 @@ var _SinglyLinkedList = class _SinglyLinkedList extends LinearLinkedBase {
983
1109
  return true;
984
1110
  }
985
1111
  /**
986
- * Check whether the list is empty.
987
- * @remarks Time O(1), Space O(1)
988
- * @returns True if length is 0.
989
- */
1112
+ * Check whether the list is empty.
1113
+ * @remarks Time O(1), Space O(1)
1114
+ * @returns True if length is 0.
1115
+
1116
+
1117
+
1118
+
1119
+
1120
+
1121
+
1122
+
1123
+
1124
+ * @example
1125
+ * // Check empty
1126
+ * console.log(new SinglyLinkedList().isEmpty()); // true;
1127
+ */
990
1128
  isEmpty() {
991
1129
  return this._length === 0;
992
1130
  }
993
1131
  /**
994
- * Remove all nodes and reset length.
995
- * @remarks Time O(N), Space O(1)
996
- * @returns void
997
- */
1132
+ * Remove all nodes and reset length.
1133
+ * @remarks Time O(N), Space O(1)
1134
+ * @returns void
1135
+
1136
+
1137
+
1138
+
1139
+
1140
+
1141
+
1142
+
1143
+
1144
+ * @example
1145
+ * // Remove all
1146
+ * const list = new SinglyLinkedList<number>([1, 2, 3]);
1147
+ * list.clear();
1148
+ * console.log(list.isEmpty()); // true;
1149
+ */
998
1150
  clear() {
999
1151
  this._head = void 0;
1000
1152
  this._tail = void 0;
1001
1153
  this._length = 0;
1002
1154
  }
1003
1155
  /**
1004
- * Reverse the list in place.
1005
- * @remarks Time O(N), Space O(1)
1006
- * @returns This list.
1007
- */
1156
+ * Reverse the list in place.
1157
+ * @remarks Time O(N), Space O(1)
1158
+ * @returns This list.
1159
+
1160
+
1161
+
1162
+
1163
+
1164
+
1165
+
1166
+
1167
+
1168
+
1169
+
1170
+ * @example
1171
+ * // Reverse the list in-place
1172
+ * const list = new SinglyLinkedList<number>([1, 2, 3, 4]);
1173
+ * list.reverse();
1174
+ * console.log([...list]); // [4, 3, 2, 1];
1175
+ */
1008
1176
  reverse() {
1009
1177
  if (!this.head || this.head === this.tail) return this;
1010
1178
  let prev;
@@ -1179,22 +1347,64 @@ var _SinglyLinkedList = class _SinglyLinkedList extends LinearLinkedBase {
1179
1347
  return false;
1180
1348
  }
1181
1349
  /**
1182
- * Deep clone this list (values are copied by reference).
1183
- * @remarks Time O(N), Space O(N)
1184
- * @returns A new list with the same element sequence.
1185
- */
1350
+ * Deep clone this list (values are copied by reference).
1351
+ * @remarks Time O(N), Space O(N)
1352
+ * @returns A new list with the same element sequence.
1353
+
1354
+
1355
+
1356
+
1357
+
1358
+
1359
+
1360
+
1361
+
1362
+ * @example
1363
+ * // Deep copy
1364
+ * const list = new SinglyLinkedList<number>([1, 2, 3]);
1365
+ * const copy = list.clone();
1366
+ * copy.pop();
1367
+ * console.log(list.length); // 3;
1368
+ * console.log(copy.length); // 2;
1369
+ */
1186
1370
  clone() {
1187
1371
  const out = this._createInstance();
1188
1372
  for (const v of this) out.push(v);
1189
1373
  return out;
1190
1374
  }
1191
1375
  /**
1192
- * Filter values into a new list of the same class.
1193
- * @remarks Time O(N), Space O(N)
1194
- * @param callback - Predicate (value, index, list) → boolean to keep value.
1195
- * @param [thisArg] - Value for `this` inside the callback.
1196
- * @returns A new list with kept values.
1197
- */
1376
+ * Filter values into a new list of the same class.
1377
+ * @remarks Time O(N), Space O(N)
1378
+ * @param callback - Predicate (value, index, list) → boolean to keep value.
1379
+ * @param [thisArg] - Value for `this` inside the callback.
1380
+ * @returns A new list with kept values.
1381
+
1382
+
1383
+
1384
+
1385
+
1386
+
1387
+
1388
+
1389
+
1390
+
1391
+
1392
+ * @example
1393
+ * // SinglyLinkedList filter and map operations
1394
+ * const list = new SinglyLinkedList<number>([1, 2, 3, 4, 5]);
1395
+ *
1396
+ * // Filter even numbers
1397
+ * const filtered = list.filter(value => value % 2 === 0);
1398
+ * console.log(filtered.length); // 2;
1399
+ *
1400
+ * // Map to double values
1401
+ * const doubled = list.map(value => value * 2);
1402
+ * console.log(doubled.length); // 5;
1403
+ *
1404
+ * // Use reduce to sum
1405
+ * const sum = list.reduce((acc, value) => acc + value, 0);
1406
+ * console.log(sum); // 15;
1407
+ */
1198
1408
  filter(callback, thisArg) {
1199
1409
  const out = this._createInstance();
1200
1410
  let index = 0;
@@ -1218,15 +1428,31 @@ var _SinglyLinkedList = class _SinglyLinkedList extends LinearLinkedBase {
1218
1428
  return out;
1219
1429
  }
1220
1430
  /**
1221
- * Map values into a new list (possibly different element type).
1222
- * @remarks Time O(N), Space O(N)
1223
- * @template EM
1224
- * @template RM
1225
- * @param callback - Mapping function (value, index, list) → newElement.
1226
- * @param [options] - Options for the output list (e.g., maxLen, toElementFn).
1227
- * @param [thisArg] - Value for `this` inside the callback.
1228
- * @returns A new SinglyLinkedList with mapped values.
1229
- */
1431
+ * Map values into a new list (possibly different element type).
1432
+ * @remarks Time O(N), Space O(N)
1433
+ * @template EM
1434
+ * @template RM
1435
+ * @param callback - Mapping function (value, index, list) → newElement.
1436
+ * @param [options] - Options for the output list (e.g., maxLen, toElementFn).
1437
+ * @param [thisArg] - Value for `this` inside the callback.
1438
+ * @returns A new SinglyLinkedList with mapped values.
1439
+
1440
+
1441
+
1442
+
1443
+
1444
+
1445
+
1446
+
1447
+
1448
+
1449
+
1450
+ * @example
1451
+ * // Transform elements
1452
+ * const list = new SinglyLinkedList<number>([1, 2, 3]);
1453
+ * const doubled = list.map(n => n * 2);
1454
+ * console.log([...doubled]); // [2, 4, 6];
1455
+ */
1230
1456
  map(callback, options, thisArg) {
1231
1457
  const out = this._createLike([], { ...options != null ? options : {}, maxLen: this._maxLen });
1232
1458
  let index = 0;
@@ -1502,11 +1728,37 @@ var _DoublyLinkedList = class _DoublyLinkedList extends LinearLinkedBase {
1502
1728
  return elementNodeOrPredicate instanceof DoublyLinkedListNode;
1503
1729
  }
1504
1730
  /**
1505
- * Append an element/node to the tail.
1506
- * @remarks Time O(1), Space O(1)
1507
- * @param elementOrNode - Element or node to append.
1508
- * @returns True when appended.
1509
- */
1731
+ * Append an element/node to the tail.
1732
+ * @remarks Time O(1), Space O(1)
1733
+ * @param elementOrNode - Element or node to append.
1734
+ * @returns True when appended.
1735
+
1736
+
1737
+
1738
+
1739
+
1740
+
1741
+
1742
+
1743
+
1744
+
1745
+
1746
+ * @example
1747
+ * // basic DoublyLinkedList creation and push operation
1748
+ * // Create a simple DoublyLinkedList with initial values
1749
+ * const list = new DoublyLinkedList([1, 2, 3, 4, 5]);
1750
+ *
1751
+ * // Verify the list maintains insertion order
1752
+ * console.log([...list]); // [1, 2, 3, 4, 5];
1753
+ *
1754
+ * // Check length
1755
+ * console.log(list.length); // 5;
1756
+ *
1757
+ * // Push a new element to the end
1758
+ * list.push(6);
1759
+ * console.log(list.length); // 6;
1760
+ * console.log([...list]); // [1, 2, 3, 4, 5, 6];
1761
+ */
1510
1762
  push(elementOrNode) {
1511
1763
  const newNode = this._ensureNode(elementOrNode);
1512
1764
  if (!this.head) {
@@ -1522,10 +1774,36 @@ var _DoublyLinkedList = class _DoublyLinkedList extends LinearLinkedBase {
1522
1774
  return true;
1523
1775
  }
1524
1776
  /**
1525
- * Remove and return the tail element.
1526
- * @remarks Time O(1), Space O(1)
1527
- * @returns Removed element or undefined.
1528
- */
1777
+ * Remove and return the tail element.
1778
+ * @remarks Time O(1), Space O(1)
1779
+ * @returns Removed element or undefined.
1780
+
1781
+
1782
+
1783
+
1784
+
1785
+
1786
+
1787
+
1788
+
1789
+
1790
+
1791
+ * @example
1792
+ * // DoublyLinkedList pop and shift operations
1793
+ * const list = new DoublyLinkedList<number>([10, 20, 30, 40, 50]);
1794
+ *
1795
+ * // Pop removes from the end
1796
+ * const last = list.pop();
1797
+ * console.log(last); // 50;
1798
+ *
1799
+ * // Shift removes from the beginning
1800
+ * const first = list.shift();
1801
+ * console.log(first); // 10;
1802
+ *
1803
+ * // Verify remaining elements
1804
+ * console.log([...list]); // [20, 30, 40];
1805
+ * console.log(list.length); // 3;
1806
+ */
1529
1807
  pop() {
1530
1808
  if (!this.tail) return void 0;
1531
1809
  const removed = this.tail;
@@ -1540,10 +1818,26 @@ var _DoublyLinkedList = class _DoublyLinkedList extends LinearLinkedBase {
1540
1818
  return removed.value;
1541
1819
  }
1542
1820
  /**
1543
- * Remove and return the head element.
1544
- * @remarks Time O(1), Space O(1)
1545
- * @returns Removed element or undefined.
1546
- */
1821
+ * Remove and return the head element.
1822
+ * @remarks Time O(1), Space O(1)
1823
+ * @returns Removed element or undefined.
1824
+
1825
+
1826
+
1827
+
1828
+
1829
+
1830
+
1831
+
1832
+
1833
+
1834
+
1835
+ * @example
1836
+ * // Remove from the front
1837
+ * const list = new DoublyLinkedList<number>([10, 20, 30]);
1838
+ * console.log(list.shift()); // 10;
1839
+ * console.log(list.first); // 20;
1840
+ */
1547
1841
  shift() {
1548
1842
  if (!this.head) return void 0;
1549
1843
  const removed = this.head;
@@ -1558,11 +1852,27 @@ var _DoublyLinkedList = class _DoublyLinkedList extends LinearLinkedBase {
1558
1852
  return removed.value;
1559
1853
  }
1560
1854
  /**
1561
- * Prepend an element/node to the head.
1562
- * @remarks Time O(1), Space O(1)
1563
- * @param elementOrNode - Element or node to prepend.
1564
- * @returns True when prepended.
1565
- */
1855
+ * Prepend an element/node to the head.
1856
+ * @remarks Time O(1), Space O(1)
1857
+ * @param elementOrNode - Element or node to prepend.
1858
+ * @returns True when prepended.
1859
+
1860
+
1861
+
1862
+
1863
+
1864
+
1865
+
1866
+
1867
+
1868
+
1869
+
1870
+ * @example
1871
+ * // Add to the front
1872
+ * const list = new DoublyLinkedList<number>([2, 3]);
1873
+ * list.unshift(1);
1874
+ * console.log([...list]); // [1, 2, 3];
1875
+ */
1566
1876
  unshift(elementOrNode) {
1567
1877
  const newNode = this._ensureNode(elementOrNode);
1568
1878
  if (!this.head) {
@@ -1606,11 +1916,27 @@ var _DoublyLinkedList = class _DoublyLinkedList extends LinearLinkedBase {
1606
1916
  return ans;
1607
1917
  }
1608
1918
  /**
1609
- * Get the element at a given index.
1610
- * @remarks Time O(N), Space O(1)
1611
- * @param index - Zero-based index.
1612
- * @returns Element or undefined.
1613
- */
1919
+ * Get the element at a given index.
1920
+ * @remarks Time O(N), Space O(1)
1921
+ * @param index - Zero-based index.
1922
+ * @returns Element or undefined.
1923
+
1924
+
1925
+
1926
+
1927
+
1928
+
1929
+
1930
+
1931
+
1932
+
1933
+
1934
+ * @example
1935
+ * // Access by index
1936
+ * const list = new DoublyLinkedList<string>(['a', 'b', 'c']);
1937
+ * console.log(list.at(1)); // 'b';
1938
+ * console.log(list.at(2)); // 'c';
1939
+ */
1614
1940
  at(index) {
1615
1941
  if (index < 0 || index >= this._length) return void 0;
1616
1942
  let current = this.head;
@@ -1618,11 +1944,23 @@ var _DoublyLinkedList = class _DoublyLinkedList extends LinearLinkedBase {
1618
1944
  return current == null ? void 0 : current.value;
1619
1945
  }
1620
1946
  /**
1621
- * Get the node reference at a given index.
1622
- * @remarks Time O(N), Space O(1)
1623
- * @param index - Zero-based index.
1624
- * @returns Node or undefined.
1625
- */
1947
+ * Get the node reference at a given index.
1948
+ * @remarks Time O(N), Space O(1)
1949
+ * @param index - Zero-based index.
1950
+ * @returns Node or undefined.
1951
+
1952
+
1953
+
1954
+
1955
+
1956
+
1957
+
1958
+
1959
+ * @example
1960
+ * // Get node at index
1961
+ * const list = new DoublyLinkedList<string>(['a', 'b', 'c']);
1962
+ * console.log(list.getNodeAt(1)?.value); // 'b';
1963
+ */
1626
1964
  getNodeAt(index) {
1627
1965
  if (index < 0 || index >= this._length) return void 0;
1628
1966
  let current = this.head;
@@ -1661,12 +1999,25 @@ var _DoublyLinkedList = class _DoublyLinkedList extends LinearLinkedBase {
1661
1999
  return void 0;
1662
2000
  }
1663
2001
  /**
1664
- * Insert a new element/node at an index, shifting following nodes.
1665
- * @remarks Time O(N), Space O(1)
1666
- * @param index - Zero-based index.
1667
- * @param newElementOrNode - Element or node to insert.
1668
- * @returns True if inserted.
1669
- */
2002
+ * Insert a new element/node at an index, shifting following nodes.
2003
+ * @remarks Time O(N), Space O(1)
2004
+ * @param index - Zero-based index.
2005
+ * @param newElementOrNode - Element or node to insert.
2006
+ * @returns True if inserted.
2007
+
2008
+
2009
+
2010
+
2011
+
2012
+
2013
+
2014
+
2015
+ * @example
2016
+ * // Insert at position
2017
+ * const list = new DoublyLinkedList<number>([1, 3]);
2018
+ * list.addAt(1, 2);
2019
+ * console.log(list.toArray()); // [1, 2, 3];
2020
+ */
1670
2021
  addAt(index, newElementOrNode) {
1671
2022
  if (index < 0 || index > this._length) return false;
1672
2023
  if (index === 0) return this.unshift(newElementOrNode);
@@ -1733,11 +2084,24 @@ var _DoublyLinkedList = class _DoublyLinkedList extends LinearLinkedBase {
1733
2084
  return true;
1734
2085
  }
1735
2086
  /**
1736
- * Delete the element at an index.
1737
- * @remarks Time O(N), Space O(1)
1738
- * @param index - Zero-based index.
1739
- * @returns Removed element or undefined.
1740
- */
2087
+ * Delete the element at an index.
2088
+ * @remarks Time O(N), Space O(1)
2089
+ * @param index - Zero-based index.
2090
+ * @returns Removed element or undefined.
2091
+
2092
+
2093
+
2094
+
2095
+
2096
+
2097
+
2098
+
2099
+ * @example
2100
+ * // Remove by index
2101
+ * const list = new DoublyLinkedList<string>(['a', 'b', 'c']);
2102
+ * list.deleteAt(1);
2103
+ * console.log(list.toArray()); // ['a', 'c'];
2104
+ */
1741
2105
  deleteAt(index) {
1742
2106
  if (index < 0 || index >= this._length) return;
1743
2107
  if (index === 0) return this.shift();
@@ -1751,11 +2115,24 @@ var _DoublyLinkedList = class _DoublyLinkedList extends LinearLinkedBase {
1751
2115
  return removedNode.value;
1752
2116
  }
1753
2117
  /**
1754
- * Delete the first match by value/node.
1755
- * @remarks Time O(N), Space O(1)
1756
- * @param [elementOrNode] - Element or node to remove.
1757
- * @returns True if removed.
1758
- */
2118
+ * Delete the first match by value/node.
2119
+ * @remarks Time O(N), Space O(1)
2120
+ * @param [elementOrNode] - Element or node to remove.
2121
+ * @returns True if removed.
2122
+
2123
+
2124
+
2125
+
2126
+
2127
+
2128
+
2129
+
2130
+ * @example
2131
+ * // Remove first occurrence
2132
+ * const list = new DoublyLinkedList<number>([1, 2, 3, 2]);
2133
+ * list.delete(2);
2134
+ * console.log(list.toArray()); // [1, 3, 2];
2135
+ */
1759
2136
  delete(elementOrNode) {
1760
2137
  const node = this.getNode(elementOrNode);
1761
2138
  if (!node) return false;
@@ -1771,29 +2148,68 @@ var _DoublyLinkedList = class _DoublyLinkedList extends LinearLinkedBase {
1771
2148
  return true;
1772
2149
  }
1773
2150
  /**
1774
- * Check whether the list is empty.
1775
- * @remarks Time O(1), Space O(1)
1776
- * @returns True if length is 0.
1777
- */
2151
+ * Check whether the list is empty.
2152
+ * @remarks Time O(1), Space O(1)
2153
+ * @returns True if length is 0.
2154
+
2155
+
2156
+
2157
+
2158
+
2159
+
2160
+
2161
+
2162
+
2163
+ * @example
2164
+ * // Check empty
2165
+ * console.log(new DoublyLinkedList().isEmpty()); // true;
2166
+ */
1778
2167
  isEmpty() {
1779
2168
  return this._length === 0;
1780
2169
  }
1781
2170
  /**
1782
- * Remove all nodes and reset length.
1783
- * @remarks Time O(N), Space O(1)
1784
- * @returns void
1785
- */
2171
+ * Remove all nodes and reset length.
2172
+ * @remarks Time O(N), Space O(1)
2173
+ * @returns void
2174
+
2175
+
2176
+
2177
+
2178
+
2179
+
2180
+
2181
+
2182
+
2183
+ * @example
2184
+ * // Remove all
2185
+ * const list = new DoublyLinkedList<number>([1, 2]);
2186
+ * list.clear();
2187
+ * console.log(list.isEmpty()); // true;
2188
+ */
1786
2189
  clear() {
1787
2190
  this._head = void 0;
1788
2191
  this._tail = void 0;
1789
2192
  this._length = 0;
1790
2193
  }
1791
2194
  /**
1792
- * Find the first value matching a predicate scanning forward.
1793
- * @remarks Time O(N), Space O(1)
1794
- * @param elementNodeOrPredicate - Element, node, or predicate to match.
1795
- * @returns Matched value or undefined.
1796
- */
2195
+ * Find the first value matching a predicate scanning forward.
2196
+ * @remarks Time O(N), Space O(1)
2197
+ * @param elementNodeOrPredicate - Element, node, or predicate to match.
2198
+ * @returns Matched value or undefined.
2199
+
2200
+
2201
+
2202
+
2203
+
2204
+
2205
+
2206
+
2207
+ * @example
2208
+ * // Search with predicate
2209
+ * const list = new DoublyLinkedList<number>([10, 20, 30]);
2210
+ * const found = list.search(node => node.value > 15);
2211
+ * console.log(found); // 20;
2212
+ */
1797
2213
  search(elementNodeOrPredicate) {
1798
2214
  const predicate = this._ensurePredicate(elementNodeOrPredicate);
1799
2215
  let current = this.head;
@@ -1804,11 +2220,25 @@ var _DoublyLinkedList = class _DoublyLinkedList extends LinearLinkedBase {
1804
2220
  return void 0;
1805
2221
  }
1806
2222
  /**
1807
- * Find the first value matching a predicate scanning backward.
1808
- * @remarks Time O(N), Space O(1)
1809
- * @param elementNodeOrPredicate - Element, node, or predicate to match.
1810
- * @returns Matched value or undefined.
1811
- */
2223
+ * Find the first value matching a predicate scanning backward.
2224
+ * @remarks Time O(N), Space O(1)
2225
+ * @param elementNodeOrPredicate - Element, node, or predicate to match.
2226
+ * @returns Matched value or undefined.
2227
+
2228
+
2229
+
2230
+
2231
+
2232
+
2233
+
2234
+
2235
+ * @example
2236
+ * // Find value scanning from tail
2237
+ * const list = new DoublyLinkedList<number>([1, 2, 3, 4]);
2238
+ * // getBackward scans from tail to head, returns first match
2239
+ * const found = list.getBackward(node => node.value < 4);
2240
+ * console.log(found); // 3;
2241
+ */
1812
2242
  getBackward(elementNodeOrPredicate) {
1813
2243
  const predicate = this._ensurePredicate(elementNodeOrPredicate);
1814
2244
  let current = this.tail;
@@ -1819,10 +2249,26 @@ var _DoublyLinkedList = class _DoublyLinkedList extends LinearLinkedBase {
1819
2249
  return void 0;
1820
2250
  }
1821
2251
  /**
1822
- * Reverse the list in place.
1823
- * @remarks Time O(N), Space O(1)
1824
- * @returns This list.
1825
- */
2252
+ * Reverse the list in place.
2253
+ * @remarks Time O(N), Space O(1)
2254
+ * @returns This list.
2255
+
2256
+
2257
+
2258
+
2259
+
2260
+
2261
+
2262
+
2263
+
2264
+
2265
+
2266
+ * @example
2267
+ * // Reverse in-place
2268
+ * const list = new DoublyLinkedList<number>([1, 2, 3]);
2269
+ * list.reverse();
2270
+ * console.log([...list]); // [3, 2, 1];
2271
+ */
1826
2272
  reverse() {
1827
2273
  let current = this.head;
1828
2274
  [this._head, this._tail] = [this.tail, this.head];
@@ -1844,22 +2290,53 @@ var _DoublyLinkedList = class _DoublyLinkedList extends LinearLinkedBase {
1844
2290
  return this;
1845
2291
  }
1846
2292
  /**
1847
- * Deep clone this list (values are copied by reference).
1848
- * @remarks Time O(N), Space O(N)
1849
- * @returns A new list with the same element sequence.
1850
- */
2293
+ * Deep clone this list (values are copied by reference).
2294
+ * @remarks Time O(N), Space O(N)
2295
+ * @returns A new list with the same element sequence.
2296
+
2297
+
2298
+
2299
+
2300
+
2301
+
2302
+
2303
+
2304
+
2305
+ * @example
2306
+ * // Deep copy
2307
+ * const list = new DoublyLinkedList<number>([1, 2, 3]);
2308
+ * const copy = list.clone();
2309
+ * copy.pop();
2310
+ * console.log(list.length); // 3;
2311
+ */
1851
2312
  clone() {
1852
2313
  const out = this._createInstance({ toElementFn: this._toElementFn, maxLen: this._maxLen });
1853
2314
  for (const v of this) out.push(v);
1854
2315
  return out;
1855
2316
  }
1856
2317
  /**
1857
- * Filter values into a new list of the same class.
1858
- * @remarks Time O(N), Space O(N)
1859
- * @param callback - Predicate (value, index, list) → boolean to keep value.
1860
- * @param [thisArg] - Value for `this` inside the callback.
1861
- * @returns A new list with kept values.
1862
- */
2318
+ * Filter values into a new list of the same class.
2319
+ * @remarks Time O(N), Space O(N)
2320
+ * @param callback - Predicate (value, index, list) → boolean to keep value.
2321
+ * @param [thisArg] - Value for `this` inside the callback.
2322
+ * @returns A new list with kept values.
2323
+
2324
+
2325
+
2326
+
2327
+
2328
+
2329
+
2330
+
2331
+
2332
+
2333
+
2334
+ * @example
2335
+ * // Filter elements
2336
+ * const list = new DoublyLinkedList<number>([1, 2, 3, 4, 5]);
2337
+ * const evens = list.filter(n => n % 2 === 0);
2338
+ * console.log([...evens]); // [2, 4];
2339
+ */
1863
2340
  filter(callback, thisArg) {
1864
2341
  const out = this._createInstance({ toElementFn: this._toElementFn, maxLen: this._maxLen });
1865
2342
  let index = 0;
@@ -1883,15 +2360,40 @@ var _DoublyLinkedList = class _DoublyLinkedList extends LinearLinkedBase {
1883
2360
  return out;
1884
2361
  }
1885
2362
  /**
1886
- * Map values into a new list (possibly different element type).
1887
- * @remarks Time O(N), Space O(N)
1888
- * @template EM
1889
- * @template RM
1890
- * @param callback - Mapping function (value, index, list) → newElement.
1891
- * @param [options] - Options for the output list (e.g., maxLen, toElementFn).
1892
- * @param [thisArg] - Value for `this` inside the callback.
1893
- * @returns A new DoublyLinkedList with mapped values.
1894
- */
2363
+ * Map values into a new list (possibly different element type).
2364
+ * @remarks Time O(N), Space O(N)
2365
+ * @template EM
2366
+ * @template RM
2367
+ * @param callback - Mapping function (value, index, list) → newElement.
2368
+ * @param [options] - Options for the output list (e.g., maxLen, toElementFn).
2369
+ * @param [thisArg] - Value for `this` inside the callback.
2370
+ * @returns A new DoublyLinkedList with mapped values.
2371
+
2372
+
2373
+
2374
+
2375
+
2376
+
2377
+
2378
+
2379
+
2380
+
2381
+
2382
+ * @example
2383
+ * // DoublyLinkedList for...of iteration and map operation
2384
+ * const list = new DoublyLinkedList<number>([1, 2, 3, 4, 5]);
2385
+ *
2386
+ * // Iterate through list
2387
+ * const doubled = list.map(value => value * 2);
2388
+ * console.log(doubled.length); // 5;
2389
+ *
2390
+ * // Use for...of loop
2391
+ * const result: number[] = [];
2392
+ * for (const item of list) {
2393
+ * result.push(item);
2394
+ * }
2395
+ * console.log(result); // [1, 2, 3, 4, 5];
2396
+ */
1895
2397
  map(callback, options, thisArg) {
1896
2398
  const out = this._createLike([], { ...options != null ? options : {}, maxLen: this._maxLen });
1897
2399
  let index = 0;
@@ -1982,6 +2484,235 @@ var _DoublyLinkedList = class _DoublyLinkedList extends LinearLinkedBase {
1982
2484
  __name(_DoublyLinkedList, "DoublyLinkedList");
1983
2485
  var DoublyLinkedList = _DoublyLinkedList;
1984
2486
 
2487
+ // src/common/error.ts
2488
+ var ERR = {
2489
+ // Range / index
2490
+ indexOutOfRange: /* @__PURE__ */ __name((index, min, max, ctx) => `${ctx ? ctx + ": " : ""}Index ${index} is out of range [${min}, ${max}].`, "indexOutOfRange"),
2491
+ invalidIndex: /* @__PURE__ */ __name((ctx) => `${ctx ? ctx + ": " : ""}Index must be an integer.`, "invalidIndex"),
2492
+ // Type / argument
2493
+ invalidArgument: /* @__PURE__ */ __name((reason, ctx) => `${ctx ? ctx + ": " : ""}${reason}`, "invalidArgument"),
2494
+ comparatorRequired: /* @__PURE__ */ __name((ctx) => `${ctx ? ctx + ": " : ""}Comparator is required for non-number/non-string/non-Date keys.`, "comparatorRequired"),
2495
+ invalidKey: /* @__PURE__ */ __name((reason, ctx) => `${ctx ? ctx + ": " : ""}${reason}`, "invalidKey"),
2496
+ notAFunction: /* @__PURE__ */ __name((name, ctx) => `${ctx ? ctx + ": " : ""}${name} must be a function.`, "notAFunction"),
2497
+ invalidEntry: /* @__PURE__ */ __name((ctx) => `${ctx ? ctx + ": " : ""}Each entry must be a [key, value] tuple.`, "invalidEntry"),
2498
+ invalidNaN: /* @__PURE__ */ __name((ctx) => `${ctx ? ctx + ": " : ""}NaN is not a valid key.`, "invalidNaN"),
2499
+ invalidDate: /* @__PURE__ */ __name((ctx) => `${ctx ? ctx + ": " : ""}Invalid Date key.`, "invalidDate"),
2500
+ reduceEmpty: /* @__PURE__ */ __name((ctx) => `${ctx ? ctx + ": " : ""}Reduce of empty structure with no initial value.`, "reduceEmpty"),
2501
+ callbackReturnType: /* @__PURE__ */ __name((expected, got, ctx) => `${ctx ? ctx + ": " : ""}Callback must return ${expected}; got ${got}.`, "callbackReturnType"),
2502
+ // State / operation
2503
+ invalidOperation: /* @__PURE__ */ __name((reason, ctx) => `${ctx ? ctx + ": " : ""}${reason}`, "invalidOperation"),
2504
+ // Matrix
2505
+ matrixDimensionMismatch: /* @__PURE__ */ __name((op) => `Matrix: Dimensions must be compatible for ${op}.`, "matrixDimensionMismatch"),
2506
+ matrixSingular: /* @__PURE__ */ __name(() => "Matrix: Singular matrix, inverse does not exist.", "matrixSingular"),
2507
+ matrixNotSquare: /* @__PURE__ */ __name(() => "Matrix: Must be square for inversion.", "matrixNotSquare"),
2508
+ matrixNotRectangular: /* @__PURE__ */ __name(() => "Matrix: Must be rectangular for transposition.", "matrixNotRectangular"),
2509
+ matrixRowMismatch: /* @__PURE__ */ __name((expected, got) => `Matrix: Expected row length ${expected}, but got ${got}.`, "matrixRowMismatch")
2510
+ };
2511
+
2512
+ // src/common/index.ts
2513
+ var DFSOperation = /* @__PURE__ */ ((DFSOperation2) => {
2514
+ DFSOperation2[DFSOperation2["VISIT"] = 0] = "VISIT";
2515
+ DFSOperation2[DFSOperation2["PROCESS"] = 1] = "PROCESS";
2516
+ return DFSOperation2;
2517
+ })(DFSOperation || {});
2518
+ var _Range = class _Range {
2519
+ constructor(low, high, includeLow = true, includeHigh = true) {
2520
+ this.low = low;
2521
+ this.high = high;
2522
+ this.includeLow = includeLow;
2523
+ this.includeHigh = includeHigh;
2524
+ }
2525
+ // Determine whether a key is within the range
2526
+ isInRange(key, comparator) {
2527
+ const lowCheck = this.includeLow ? comparator(key, this.low) >= 0 : comparator(key, this.low) > 0;
2528
+ const highCheck = this.includeHigh ? comparator(key, this.high) <= 0 : comparator(key, this.high) < 0;
2529
+ return lowCheck && highCheck;
2530
+ }
2531
+ };
2532
+ __name(_Range, "Range");
2533
+ var Range = _Range;
2534
+
2535
+ // src/data-structures/base/iterable-entry-base.ts
2536
+ var _IterableEntryBase = class _IterableEntryBase {
2537
+ /**
2538
+ * Default iterator yielding `[key, value]` entries.
2539
+ * @returns Iterator of `[K, V]`.
2540
+ * @remarks Time O(n) to iterate, Space O(1)
2541
+ */
2542
+ *[Symbol.iterator](...args) {
2543
+ yield* this._getIterator(...args);
2544
+ }
2545
+ /**
2546
+ * Iterate over `[key, value]` pairs (may yield `undefined` values).
2547
+ * @returns Iterator of `[K, V | undefined]`.
2548
+ * @remarks Time O(n), Space O(1)
2549
+ */
2550
+ *entries() {
2551
+ for (const item of this) {
2552
+ yield item;
2553
+ }
2554
+ }
2555
+ /**
2556
+ * Iterate over keys only.
2557
+ * @returns Iterator of keys.
2558
+ * @remarks Time O(n), Space O(1)
2559
+ */
2560
+ *keys() {
2561
+ for (const item of this) {
2562
+ yield item[0];
2563
+ }
2564
+ }
2565
+ /**
2566
+ * Iterate over values only.
2567
+ * @returns Iterator of values.
2568
+ * @remarks Time O(n), Space O(1)
2569
+ */
2570
+ *values() {
2571
+ for (const item of this) {
2572
+ yield item[1];
2573
+ }
2574
+ }
2575
+ /**
2576
+ * Test whether all entries satisfy the predicate.
2577
+ * @param predicate - `(key, value, index, self) => boolean`.
2578
+ * @param thisArg - Optional `this` for callback.
2579
+ * @returns `true` if all pass; otherwise `false`.
2580
+ * @remarks Time O(n), Space O(1)
2581
+ */
2582
+ every(predicate, thisArg) {
2583
+ let index = 0;
2584
+ for (const item of this) {
2585
+ if (!predicate.call(thisArg, item[1], item[0], index++, this)) {
2586
+ return false;
2587
+ }
2588
+ }
2589
+ return true;
2590
+ }
2591
+ /**
2592
+ * Test whether any entry satisfies the predicate.
2593
+ * @param predicate - `(key, value, index, self) => boolean`.
2594
+ * @param thisArg - Optional `this` for callback.
2595
+ * @returns `true` if any passes; otherwise `false`.
2596
+ * @remarks Time O(n), Space O(1)
2597
+ */
2598
+ some(predicate, thisArg) {
2599
+ let index = 0;
2600
+ for (const item of this) {
2601
+ if (predicate.call(thisArg, item[1], item[0], index++, this)) {
2602
+ return true;
2603
+ }
2604
+ }
2605
+ return false;
2606
+ }
2607
+ /**
2608
+ * Visit each entry, left-to-right.
2609
+ * @param callbackfn - `(key, value, index, self) => void`.
2610
+ * @param thisArg - Optional `this` for callback.
2611
+ * @remarks Time O(n), Space O(1)
2612
+ */
2613
+ forEach(callbackfn, thisArg) {
2614
+ let index = 0;
2615
+ for (const item of this) {
2616
+ const [key, value] = item;
2617
+ callbackfn.call(thisArg, value, key, index++, this);
2618
+ }
2619
+ }
2620
+ /**
2621
+ * Find the first entry that matches a predicate.
2622
+ * @param callbackfn - `(key, value, index, self) => boolean`.
2623
+ * @param thisArg - Optional `this` for callback.
2624
+ * @returns Matching `[key, value]` or `undefined`.
2625
+ * @remarks Time O(n), Space O(1)
2626
+ */
2627
+ find(callbackfn, thisArg) {
2628
+ let index = 0;
2629
+ for (const item of this) {
2630
+ const [key, value] = item;
2631
+ if (callbackfn.call(thisArg, value, key, index++, this)) return item;
2632
+ }
2633
+ return;
2634
+ }
2635
+ /**
2636
+ * Whether the given key exists.
2637
+ * @param key - Key to test.
2638
+ * @returns `true` if found; otherwise `false`.
2639
+ * @remarks Time O(n) generic, Space O(1)
2640
+ */
2641
+ has(key) {
2642
+ for (const item of this) {
2643
+ const [itemKey] = item;
2644
+ if (itemKey === key) return true;
2645
+ }
2646
+ return false;
2647
+ }
2648
+ /**
2649
+ * Whether there exists an entry with the given value.
2650
+ * @param value - Value to test.
2651
+ * @returns `true` if found; otherwise `false`.
2652
+ * @remarks Time O(n), Space O(1)
2653
+ */
2654
+ hasValue(value) {
2655
+ for (const [, elementValue] of this) {
2656
+ if (elementValue === value) return true;
2657
+ }
2658
+ return false;
2659
+ }
2660
+ /**
2661
+ * Get the value under a key.
2662
+ * @param key - Key to look up.
2663
+ * @returns Value or `undefined`.
2664
+ * @remarks Time O(n) generic, Space O(1)
2665
+ */
2666
+ get(key) {
2667
+ for (const item of this) {
2668
+ const [itemKey, value] = item;
2669
+ if (itemKey === key) return value;
2670
+ }
2671
+ return;
2672
+ }
2673
+ /**
2674
+ * Reduce entries into a single accumulator.
2675
+ * @param callbackfn - `(acc, value, key, index, self) => acc`.
2676
+ * @param initialValue - Initial accumulator.
2677
+ * @returns Final accumulator.
2678
+ * @remarks Time O(n), Space O(1)
2679
+ */
2680
+ reduce(callbackfn, initialValue) {
2681
+ let accumulator = initialValue;
2682
+ let index = 0;
2683
+ for (const item of this) {
2684
+ const [key, value] = item;
2685
+ accumulator = callbackfn(accumulator, value, key, index++, this);
2686
+ }
2687
+ return accumulator;
2688
+ }
2689
+ /**
2690
+ * Converts data structure to `[key, value]` pairs.
2691
+ * @returns Array of entries.
2692
+ * @remarks Time O(n), Space O(n)
2693
+ */
2694
+ toArray() {
2695
+ return [...this];
2696
+ }
2697
+ /**
2698
+ * Visualize the iterable as an array of `[key, value]` pairs (or a custom string).
2699
+ * @returns Array of entries (default) or a string.
2700
+ * @remarks Time O(n), Space O(n)
2701
+ */
2702
+ toVisual() {
2703
+ return [...this];
2704
+ }
2705
+ /**
2706
+ * Print a human-friendly representation to the console.
2707
+ * @remarks Time O(n), Space O(n)
2708
+ */
2709
+ print() {
2710
+ console.log(this.toVisual());
2711
+ }
2712
+ };
2713
+ __name(_IterableEntryBase, "IterableEntryBase");
2714
+ var IterableEntryBase = _IterableEntryBase;
2715
+
1985
2716
  // src/data-structures/linked-list/skip-linked-list.ts
1986
2717
  var _SkipListNode = class _SkipListNode {
1987
2718
  constructor(key, value, level) {
@@ -1990,31 +2721,69 @@ var _SkipListNode = class _SkipListNode {
1990
2721
  __publicField(this, "forward");
1991
2722
  this.key = key;
1992
2723
  this.value = value;
1993
- this.forward = new Array(level);
2724
+ this.forward = new Array(level).fill(void 0);
1994
2725
  }
1995
2726
  };
1996
2727
  __name(_SkipListNode, "SkipListNode");
1997
2728
  var SkipListNode = _SkipListNode;
1998
- var _SkipList = class _SkipList {
1999
- constructor(elements = [], options) {
2000
- __publicField(this, "_head", new SkipListNode(void 0, void 0, this.maxLevel));
2729
+ var _comparator, _isDefaultComparator;
2730
+ var _SkipList = class _SkipList extends IterableEntryBase {
2731
+ constructor(entries = [], options = {}) {
2732
+ super();
2733
+ __privateAdd(this, _comparator);
2734
+ __privateAdd(this, _isDefaultComparator);
2735
+ // ─── Internal state ──────────────────────────────────────────
2736
+ __publicField(this, "_head");
2001
2737
  __publicField(this, "_level", 0);
2738
+ __publicField(this, "_size", 0);
2002
2739
  __publicField(this, "_maxLevel", 16);
2003
2740
  __publicField(this, "_probability", 0.5);
2004
- if (options) {
2005
- const { maxLevel, probability } = options;
2006
- if (typeof maxLevel === "number") this._maxLevel = maxLevel;
2007
- if (typeof probability === "number") this._probability = probability;
2008
- }
2009
- if (elements) {
2010
- for (const [key, value] of elements) this.add(key, value);
2741
+ const { comparator, toEntryFn, maxLevel, probability } = options;
2742
+ if (typeof maxLevel === "number" && maxLevel > 0) this._maxLevel = maxLevel;
2743
+ if (typeof probability === "number" && probability > 0 && probability < 1) this._probability = probability;
2744
+ __privateSet(this, _isDefaultComparator, comparator === void 0);
2745
+ __privateSet(this, _comparator, comparator != null ? comparator : _SkipList.createDefaultComparator());
2746
+ this._head = new SkipListNode(void 0, void 0, this._maxLevel);
2747
+ for (const item of entries) {
2748
+ let k;
2749
+ let v;
2750
+ if (toEntryFn) {
2751
+ [k, v] = toEntryFn(item);
2752
+ } else {
2753
+ if (!Array.isArray(item) || item.length < 2) {
2754
+ throw new TypeError(ERR.invalidEntry("SkipList"));
2755
+ }
2756
+ [k, v] = item;
2757
+ }
2758
+ this.set(k, v);
2011
2759
  }
2012
2760
  }
2013
- get head() {
2014
- return this._head;
2761
+ /**
2762
+ * Creates a default comparator supporting number, string, Date, and bigint.
2763
+ */
2764
+ static createDefaultComparator() {
2765
+ return (a, b) => {
2766
+ if (typeof a === "number" && typeof b === "number") {
2767
+ if (Number.isNaN(a) || Number.isNaN(b)) throw new TypeError(ERR.invalidNaN("SkipList"));
2768
+ return a - b;
2769
+ }
2770
+ if (typeof a === "string" && typeof b === "string") {
2771
+ return a < b ? -1 : a > b ? 1 : 0;
2772
+ }
2773
+ if (a instanceof Date && b instanceof Date) {
2774
+ const ta = a.getTime(), tb = b.getTime();
2775
+ if (Number.isNaN(ta) || Number.isNaN(tb)) throw new TypeError(ERR.invalidDate("SkipList"));
2776
+ return ta - tb;
2777
+ }
2778
+ if (typeof a === "bigint" && typeof b === "bigint") {
2779
+ return a < b ? -1 : a > b ? 1 : 0;
2780
+ }
2781
+ throw new TypeError(ERR.comparatorRequired("SkipList"));
2782
+ };
2015
2783
  }
2016
- get level() {
2017
- return this._level;
2784
+ // ─── Size & lifecycle ────────────────────────────────────────
2785
+ get size() {
2786
+ return this._size;
2018
2787
  }
2019
2788
  get maxLevel() {
2020
2789
  return this._maxLevel;
@@ -2022,108 +2791,592 @@ var _SkipList = class _SkipList {
2022
2791
  get probability() {
2023
2792
  return this._probability;
2024
2793
  }
2025
- get first() {
2026
- const firstNode = this.head.forward[0];
2027
- return firstNode ? firstNode.value : void 0;
2794
+ get comparator() {
2795
+ return __privateGet(this, _comparator);
2796
+ }
2797
+ /**
2798
+ * Check if empty
2799
+
2800
+
2801
+
2802
+
2803
+
2804
+
2805
+
2806
+
2807
+ * @example
2808
+ * // Check if empty
2809
+ * const sl = new SkipList<number, string>();
2810
+ * console.log(sl.isEmpty()); // true;
2811
+ */
2812
+ isEmpty() {
2813
+ return this._size === 0;
2814
+ }
2815
+ /**
2816
+ * Remove all entries
2817
+
2818
+
2819
+
2820
+
2821
+
2822
+
2823
+
2824
+
2825
+ * @example
2826
+ * // Remove all entries
2827
+ * const sl = new SkipList<number, string>([[1, 'a'], [2, 'b']]);
2828
+ * sl.clear();
2829
+ * console.log(sl.isEmpty()); // true;
2830
+ */
2831
+ clear() {
2832
+ this._head = new SkipListNode(void 0, void 0, this._maxLevel);
2833
+ this._level = 0;
2834
+ this._size = 0;
2835
+ }
2836
+ /**
2837
+ * Create independent copy
2838
+
2839
+
2840
+
2841
+
2842
+
2843
+
2844
+
2845
+
2846
+ * @example
2847
+ * // Create independent copy
2848
+ * const sl = new SkipList<number, string>([[1, 'a'], [2, 'b']]);
2849
+ * const copy = sl.clone();
2850
+ * copy.delete(1);
2851
+ * console.log(sl.has(1)); // true;
2852
+ */
2853
+ clone() {
2854
+ return new _SkipList(this, {
2855
+ comparator: __privateGet(this, _isDefaultComparator) ? void 0 : __privateGet(this, _comparator),
2856
+ maxLevel: this._maxLevel,
2857
+ probability: this._probability
2858
+ });
2859
+ }
2860
+ // ─── Core CRUD ───────────────────────────────────────────────
2861
+ /**
2862
+ * Insert or update a key-value pair. Returns `this` for chaining.
2863
+ * Unique keys only — if key exists, value is updated in place.
2864
+
2865
+
2866
+
2867
+
2868
+
2869
+
2870
+
2871
+
2872
+
2873
+
2874
+
2875
+ * @example
2876
+ * // In-memory sorted key-value store
2877
+ * const store = new SkipList<number, string>();
2878
+ *
2879
+ * store.set(3, 'three');
2880
+ * store.set(1, 'one');
2881
+ * store.set(5, 'five');
2882
+ * store.set(2, 'two');
2883
+ *
2884
+ * console.log(store.get(3)); // 'three';
2885
+ * console.log(store.get(1)); // 'one';
2886
+ * console.log(store.get(5)); // 'five';
2887
+ *
2888
+ * // Update existing key
2889
+ * store.set(3, 'THREE');
2890
+ * console.log(store.get(3)); // 'THREE';
2891
+ */
2892
+ set(key, value) {
2893
+ const cmp = __privateGet(this, _comparator);
2894
+ const update = this._findUpdate(key);
2895
+ const existing = update[0].forward[0];
2896
+ if (existing && cmp(existing.key, key) === 0) {
2897
+ existing.value = value;
2898
+ return this;
2899
+ }
2900
+ const newLevel = this._randomLevel();
2901
+ const newNode = new SkipListNode(key, value, newLevel);
2902
+ if (newLevel > this._level) {
2903
+ for (let i = this._level; i < newLevel; i++) {
2904
+ update[i] = this._head;
2905
+ }
2906
+ this._level = newLevel;
2907
+ }
2908
+ for (let i = 0; i < newLevel; i++) {
2909
+ newNode.forward[i] = update[i].forward[i];
2910
+ update[i].forward[i] = newNode;
2911
+ }
2912
+ this._size++;
2913
+ return this;
2028
2914
  }
2029
- get last() {
2030
- let current = this.head;
2031
- for (let i = this.level - 1; i >= 0; i--) {
2915
+ /**
2916
+ * Get the value for a key, or `undefined` if not found.
2917
+ * Overrides base O(n) with O(log n) skip-list search.
2918
+
2919
+
2920
+
2921
+
2922
+
2923
+
2924
+
2925
+
2926
+
2927
+
2928
+
2929
+ * @example
2930
+ * // Building a sorted index
2931
+ * type Product = { id: number; name: string; price: number };
2932
+ * const products: Product[] = [
2933
+ * { id: 1, name: 'Widget', price: 25 },
2934
+ * { id: 2, name: 'Gadget', price: 50 },
2935
+ * { id: 3, name: 'Doohickey', price: 15 }
2936
+ * ];
2937
+ *
2938
+ * const index = new SkipList<number, Product>(products as any, {
2939
+ * toEntryFn: (p: any) => [p.price, p]
2940
+ * });
2941
+ *
2942
+ * // Iterate in sorted order by price
2943
+ * const names = [...index.values()].map(p => p!.name);
2944
+ * console.log(names); // ['Doohickey', 'Widget', 'Gadget'];
2945
+ *
2946
+ * // Range search: products between $20 and $60
2947
+ * const range = index.rangeSearch([20, 60]);
2948
+ * console.log(range.map(([, p]) => p!.name)); // ['Widget', 'Gadget'];
2949
+ */
2950
+ get(key) {
2951
+ const node = this._findNode(key);
2952
+ return node ? node.value : void 0;
2953
+ }
2954
+ /**
2955
+ * Check if a key exists.
2956
+ * Overrides base O(n) with O(log n) skip-list search.
2957
+
2958
+
2959
+
2960
+
2961
+
2962
+
2963
+
2964
+
2965
+
2966
+
2967
+
2968
+ * @example
2969
+ * // Check key existence
2970
+ * const sl = new SkipList<number, string>([[1, 'a'], [3, 'c'], [5, 'e']]);
2971
+ * console.log(sl.has(3)); // true;
2972
+ * console.log(sl.has(4)); // false;
2973
+ */
2974
+ has(key) {
2975
+ return this._findNode(key) !== void 0;
2976
+ }
2977
+ /**
2978
+ * Delete a key. Returns `true` if the key was found and removed.
2979
+
2980
+
2981
+
2982
+
2983
+
2984
+
2985
+
2986
+
2987
+
2988
+
2989
+
2990
+ * @example
2991
+ * // Fast lookup with deletion
2992
+ * const cache = new SkipList<string, number>();
2993
+ *
2994
+ * cache.set('alpha', 1);
2995
+ * cache.set('beta', 2);
2996
+ * cache.set('gamma', 3);
2997
+ *
2998
+ * console.log(cache.has('beta')); // true;
2999
+ * cache.delete('beta');
3000
+ * console.log(cache.has('beta')); // false;
3001
+ * console.log(cache.size); // 2;
3002
+ */
3003
+ delete(key) {
3004
+ const cmp = __privateGet(this, _comparator);
3005
+ const update = this._findUpdate(key);
3006
+ const target = update[0].forward[0];
3007
+ if (!target || cmp(target.key, key) !== 0) return false;
3008
+ for (let i = 0; i < this._level; i++) {
3009
+ if (update[i].forward[i] !== target) break;
3010
+ update[i].forward[i] = target.forward[i];
3011
+ }
3012
+ while (this._level > 0 && !this._head.forward[this._level - 1]) {
3013
+ this._level--;
3014
+ }
3015
+ this._size--;
3016
+ return true;
3017
+ }
3018
+ // ─── Navigation ──────────────────────────────────────────────
3019
+ /**
3020
+ * Returns the first (smallest key) entry, or `undefined` if empty.
3021
+
3022
+
3023
+
3024
+
3025
+
3026
+
3027
+
3028
+
3029
+
3030
+
3031
+
3032
+ * @example
3033
+ * // Access the minimum entry
3034
+ * const sl = new SkipList<number, string>([[5, 'e'], [1, 'a'], [3, 'c']]);
3035
+ * console.log(sl.first()); // [1, 'a'];
3036
+ */
3037
+ first() {
3038
+ const node = this._head.forward[0];
3039
+ return node ? [node.key, node.value] : void 0;
3040
+ }
3041
+ /**
3042
+ * Returns the last (largest key) entry, or `undefined` if empty.
3043
+
3044
+
3045
+
3046
+
3047
+
3048
+
3049
+
3050
+
3051
+
3052
+
3053
+
3054
+ * @example
3055
+ * // Access the maximum entry
3056
+ * const sl = new SkipList<number, string>([[5, 'e'], [1, 'a'], [3, 'c']]);
3057
+ * console.log(sl.last()); // [5, 'e'];
3058
+ */
3059
+ last() {
3060
+ let current = this._head;
3061
+ for (let i = this._level - 1; i >= 0; i--) {
2032
3062
  while (current.forward[i]) {
2033
3063
  current = current.forward[i];
2034
3064
  }
2035
3065
  }
2036
- return current.value;
2037
- }
2038
- add(key, value) {
2039
- const newNode = new SkipListNode(key, value, this._randomLevel());
2040
- const update = new Array(this.maxLevel).fill(this.head);
2041
- let current = this.head;
2042
- for (let i = this.level - 1; i >= 0; i--) {
2043
- while (current.forward[i] && current.forward[i].key < key) {
3066
+ return current === this._head ? void 0 : [current.key, current.value];
3067
+ }
3068
+ /**
3069
+ * Remove and return the first (smallest key) entry.
3070
+
3071
+
3072
+
3073
+
3074
+
3075
+
3076
+
3077
+
3078
+ * @example
3079
+ * // Remove and return smallest
3080
+ * const sl = new SkipList<number, string>([[1, 'a'], [2, 'b'], [3, 'c']]);
3081
+ * console.log(sl.pollFirst()); // [1, 'a'];
3082
+ * console.log(sl.size); // 2;
3083
+ */
3084
+ pollFirst() {
3085
+ const entry = this.first();
3086
+ if (!entry) return void 0;
3087
+ this.delete(entry[0]);
3088
+ return entry;
3089
+ }
3090
+ /**
3091
+ * Remove and return the last (largest key) entry.
3092
+
3093
+
3094
+
3095
+
3096
+
3097
+
3098
+
3099
+
3100
+ * @example
3101
+ * // Remove and return largest
3102
+ * const sl = new SkipList<number, string>([[1, 'a'], [2, 'b'], [3, 'c']]);
3103
+ * console.log(sl.pollLast()); // [3, 'c'];
3104
+ * console.log(sl.size); // 2;
3105
+ */
3106
+ pollLast() {
3107
+ const entry = this.last();
3108
+ if (!entry) return void 0;
3109
+ this.delete(entry[0]);
3110
+ return entry;
3111
+ }
3112
+ /**
3113
+ * Least entry ≥ key, or `undefined`.
3114
+
3115
+
3116
+
3117
+
3118
+
3119
+
3120
+
3121
+
3122
+
3123
+
3124
+
3125
+ * @example
3126
+ * // Least entry ≥ key
3127
+ * const sl = new SkipList<number, string>([[10, 'a'], [20, 'b'], [30, 'c']]);
3128
+ * console.log(sl.ceiling(15)); // [20, 'b'];
3129
+ * console.log(sl.ceiling(20)); // [20, 'b'];
3130
+ */
3131
+ ceiling(key) {
3132
+ const cmp = __privateGet(this, _comparator);
3133
+ let current = this._head;
3134
+ for (let i = this._level - 1; i >= 0; i--) {
3135
+ while (current.forward[i] && cmp(current.forward[i].key, key) < 0) {
2044
3136
  current = current.forward[i];
2045
3137
  }
2046
- update[i] = current;
2047
- }
2048
- for (let i = 0; i < newNode.forward.length; i++) {
2049
- newNode.forward[i] = update[i].forward[i];
2050
- update[i].forward[i] = newNode;
2051
3138
  }
2052
- if (!newNode.forward[0]) {
2053
- this._level = Math.max(this.level, newNode.forward.length);
3139
+ const node = current.forward[0];
3140
+ return node ? [node.key, node.value] : void 0;
3141
+ }
3142
+ /**
3143
+ * Greatest entry ≤ key, or `undefined`.
3144
+
3145
+
3146
+
3147
+
3148
+
3149
+
3150
+
3151
+
3152
+
3153
+
3154
+
3155
+ * @example
3156
+ * // Greatest entry ≤ key
3157
+ * const sl = new SkipList<number, string>([[10, 'a'], [20, 'b'], [30, 'c']]);
3158
+ * console.log(sl.floor(25)); // [20, 'b'];
3159
+ * console.log(sl.floor(5)); // undefined;
3160
+ */
3161
+ floor(key) {
3162
+ const cmp = __privateGet(this, _comparator);
3163
+ let current = this._head;
3164
+ for (let i = this._level - 1; i >= 0; i--) {
3165
+ while (current.forward[i] && cmp(current.forward[i].key, key) <= 0) {
3166
+ current = current.forward[i];
3167
+ }
2054
3168
  }
3169
+ const result = current === this._head ? void 0 : current;
3170
+ if (result && cmp(result.key, key) <= 0) return [result.key, result.value];
3171
+ return void 0;
2055
3172
  }
2056
- get(key) {
2057
- let current = this.head;
2058
- for (let i = this.level - 1; i >= 0; i--) {
2059
- while (current.forward[i] && current.forward[i].key < key) {
3173
+ /**
3174
+ * Least entry strictly > key, or `undefined`.
3175
+
3176
+
3177
+
3178
+
3179
+
3180
+
3181
+
3182
+
3183
+ * @example
3184
+ * // Strictly greater entry
3185
+ * const sl = new SkipList<number, string>([[10, 'a'], [20, 'b'], [30, 'c']]);
3186
+ * console.log(sl.higher(15)); // [20, 'b'];
3187
+ * console.log(sl.higher(30)); // undefined;
3188
+ */
3189
+ higher(key) {
3190
+ const cmp = __privateGet(this, _comparator);
3191
+ let current = this._head;
3192
+ for (let i = this._level - 1; i >= 0; i--) {
3193
+ while (current.forward[i] && cmp(current.forward[i].key, key) <= 0) {
2060
3194
  current = current.forward[i];
2061
3195
  }
2062
3196
  }
2063
- current = current.forward[0];
2064
- if (current && current.key === key) {
2065
- return current.value;
3197
+ const node = current.forward[0];
3198
+ return node ? [node.key, node.value] : void 0;
3199
+ }
3200
+ /**
3201
+ * Greatest entry strictly < key, or `undefined`.
3202
+
3203
+
3204
+
3205
+
3206
+
3207
+
3208
+
3209
+
3210
+ * @example
3211
+ * // Strictly less entry
3212
+ * const sl = new SkipList<number, string>([[10, 'a'], [20, 'b'], [30, 'c']]);
3213
+ * console.log(sl.lower(25)); // [20, 'b'];
3214
+ * console.log(sl.lower(10)); // undefined;
3215
+ */
3216
+ lower(key) {
3217
+ const cmp = __privateGet(this, _comparator);
3218
+ let current = this._head;
3219
+ let result;
3220
+ for (let i = this._level - 1; i >= 0; i--) {
3221
+ while (current.forward[i] && cmp(current.forward[i].key, key) < 0) {
3222
+ current = current.forward[i];
3223
+ }
3224
+ if (current !== this._head && cmp(current.key, key) < 0) {
3225
+ result = current;
3226
+ }
2066
3227
  }
2067
- return void 0;
2068
- }
2069
- has(key) {
2070
- return this.get(key) !== void 0;
2071
- }
2072
- delete(key) {
2073
- const update = new Array(this.maxLevel).fill(this.head);
2074
- let current = this.head;
2075
- for (let i = this.level - 1; i >= 0; i--) {
2076
- while (current.forward[i] && current.forward[i].key < key) {
3228
+ return result ? [result.key, result.value] : void 0;
3229
+ }
3230
+ /**
3231
+ * Returns entries within the given key range.
3232
+
3233
+
3234
+
3235
+
3236
+
3237
+
3238
+
3239
+
3240
+
3241
+
3242
+
3243
+ * @example
3244
+ * // Find entries in a range
3245
+ * const sl = new SkipList<number, string>([[1, 'a'], [2, 'b'], [3, 'c'], [4, 'd'], [5, 'e']]);
3246
+ * const result = sl.rangeSearch([2, 4]);
3247
+ * console.log(result); // [[2, 'b'], [3, 'c'], [4, 'd']];
3248
+ */
3249
+ rangeSearch(range, options = {}) {
3250
+ const { lowInclusive = true, highInclusive = true } = options;
3251
+ const [low, high] = range;
3252
+ const cmp = __privateGet(this, _comparator);
3253
+ const out = [];
3254
+ let current = this._head;
3255
+ for (let i = this._level - 1; i >= 0; i--) {
3256
+ while (current.forward[i] && cmp(current.forward[i].key, low) < 0) {
2077
3257
  current = current.forward[i];
2078
3258
  }
2079
- update[i] = current;
2080
3259
  }
2081
3260
  current = current.forward[0];
2082
- if (current && current.key === key) {
2083
- for (let i = 0; i < this.level; i++) {
2084
- if (update[i].forward[i] !== current) {
2085
- break;
2086
- }
2087
- update[i].forward[i] = current.forward[i];
2088
- }
2089
- while (this.level > 0 && !this.head.forward[this.level - 1]) {
2090
- this._level--;
3261
+ while (current) {
3262
+ const cmpHigh = cmp(current.key, high);
3263
+ if (cmpHigh > 0) break;
3264
+ if (cmpHigh === 0 && !highInclusive) break;
3265
+ const cmpLow = cmp(current.key, low);
3266
+ if (cmpLow > 0 || cmpLow === 0 && lowInclusive) {
3267
+ out.push([current.key, current.value]);
2091
3268
  }
2092
- return true;
3269
+ current = current.forward[0];
2093
3270
  }
2094
- return false;
3271
+ return out;
2095
3272
  }
2096
- higher(key) {
2097
- let current = this.head;
2098
- for (let i = this.level - 1; i >= 0; i--) {
2099
- while (current.forward[i] && current.forward[i].key <= key) {
3273
+ // ─── Functional (overrides) ──────────────────────────────────
3274
+ /**
3275
+ * Creates a new SkipList with entries transformed by callback.
3276
+
3277
+
3278
+
3279
+
3280
+
3281
+
3282
+
3283
+
3284
+ * @example
3285
+ * // Transform entries
3286
+ * const sl = new SkipList<number, string>([[1, 'a'], [2, 'b']]);
3287
+ * const mapped = sl.map((v, k) => [k, v?.toUpperCase()] as [number, string]);
3288
+ * console.log([...mapped.values()]); // ['A', 'B'];
3289
+ */
3290
+ map(callback, options) {
3291
+ const out = new _SkipList([], options != null ? options : {});
3292
+ let i = 0;
3293
+ for (const [k, v] of this) {
3294
+ const [nk, nv] = callback(v, k, i++, this);
3295
+ out.set(nk, nv);
3296
+ }
3297
+ return out;
3298
+ }
3299
+ /**
3300
+ * Creates a new SkipList with entries that pass the predicate.
3301
+
3302
+
3303
+
3304
+
3305
+
3306
+
3307
+
3308
+
3309
+ * @example
3310
+ * // Filter entries
3311
+ * const sl = new SkipList<number, string>([[1, 'a'], [2, 'b'], [3, 'c']]);
3312
+ * const result = sl.filter((v, k) => k > 1);
3313
+ * console.log(result.size); // 2;
3314
+ */
3315
+ filter(callbackfn, thisArg) {
3316
+ const out = new _SkipList([], {
3317
+ comparator: __privateGet(this, _isDefaultComparator) ? void 0 : __privateGet(this, _comparator),
3318
+ maxLevel: this._maxLevel,
3319
+ probability: this._probability
3320
+ });
3321
+ let i = 0;
3322
+ for (const [k, v] of this) {
3323
+ const ok = callbackfn.call(thisArg, v, k, i++, this);
3324
+ if (ok) out.set(k, v);
3325
+ }
3326
+ return out;
3327
+ }
3328
+ // ─── Iterator (required by IterableEntryBase) ────────────────
3329
+ _getIterator() {
3330
+ const head = this._head;
3331
+ return (function* () {
3332
+ let node = head.forward[0];
3333
+ while (node) {
3334
+ yield [node.key, node.value];
3335
+ node = node.forward[0];
3336
+ }
3337
+ })();
3338
+ }
3339
+ // ─── Internal helpers ────────────────────────────────────────
3340
+ /**
3341
+ * Finds the update array (predecessors at each level) for a given key.
3342
+ */
3343
+ _findUpdate(key) {
3344
+ const cmp = __privateGet(this, _comparator);
3345
+ const update = new Array(this._maxLevel).fill(this._head);
3346
+ let current = this._head;
3347
+ for (let i = this._level - 1; i >= 0; i--) {
3348
+ while (current.forward[i] && cmp(current.forward[i].key, key) < 0) {
2100
3349
  current = current.forward[i];
2101
3350
  }
3351
+ update[i] = current;
2102
3352
  }
2103
- const nextNode = current.forward[0];
2104
- return nextNode ? nextNode.value : void 0;
3353
+ return update;
2105
3354
  }
2106
- lower(key) {
2107
- let current = this.head;
2108
- let lastLess = void 0;
2109
- for (let i = this.level - 1; i >= 0; i--) {
2110
- while (current.forward[i] && current.forward[i].key < key) {
3355
+ /**
3356
+ * Finds the node for a given key, or undefined.
3357
+ */
3358
+ _findNode(key) {
3359
+ const cmp = __privateGet(this, _comparator);
3360
+ let current = this._head;
3361
+ for (let i = this._level - 1; i >= 0; i--) {
3362
+ while (current.forward[i] && cmp(current.forward[i].key, key) < 0) {
2111
3363
  current = current.forward[i];
2112
3364
  }
2113
- if (current.key < key) {
2114
- lastLess = current;
2115
- }
2116
3365
  }
2117
- return lastLess ? lastLess.value : void 0;
3366
+ const candidate = current.forward[0];
3367
+ if (candidate && cmp(candidate.key, key) === 0) return candidate;
3368
+ return void 0;
2118
3369
  }
2119
3370
  _randomLevel() {
2120
3371
  let level = 1;
2121
- while (Math.random() < this.probability && level < this.maxLevel) {
3372
+ while (Math.random() < this._probability && level < this._maxLevel) {
2122
3373
  level++;
2123
3374
  }
2124
3375
  return level;
2125
3376
  }
2126
3377
  };
3378
+ _comparator = new WeakMap();
3379
+ _isDefaultComparator = new WeakMap();
2127
3380
  __name(_SkipList, "SkipList");
2128
3381
  var SkipList = _SkipList;
2129
3382
  /**