@seanhogg/builderforce-memory-engine 2026.9.34 → 2026.10.1

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 (170) hide show
  1. package/dist/evermind/delta_wire.d.ts +10 -1
  2. package/dist/evermind/delta_wire.d.ts.map +1 -1
  3. package/dist/evermind/delta_wire.js +25 -3
  4. package/dist/evermind/delta_wire.js.map +1 -1
  5. package/dist/evermind/index.d.ts +4 -4
  6. package/dist/evermind/index.d.ts.map +1 -1
  7. package/dist/evermind/index.js +2 -2
  8. package/dist/evermind/index.js.map +1 -1
  9. package/dist/evermind/merge.d.ts +25 -0
  10. package/dist/evermind/merge.d.ts.map +1 -1
  11. package/dist/evermind/merge.js +30 -0
  12. package/dist/evermind/merge.js.map +1 -1
  13. package/dist/evermind/package.d.ts +9 -0
  14. package/dist/evermind/package.d.ts.map +1 -1
  15. package/dist/evermind/package.js +20 -0
  16. package/dist/evermind/package.js.map +1 -1
  17. package/dist/index.d.ts +6 -5
  18. package/dist/index.d.ts.map +1 -1
  19. package/dist/index.js +5 -3
  20. package/dist/index.js.map +1 -1
  21. package/dist/limbic/index.d.ts +3 -0
  22. package/dist/limbic/index.d.ts.map +1 -1
  23. package/dist/limbic/index.js +3 -0
  24. package/dist/limbic/index.js.map +1 -1
  25. package/dist/limbic/limbic_task.d.ts +22 -0
  26. package/dist/limbic/limbic_task.d.ts.map +1 -0
  27. package/dist/limbic/limbic_task.js +45 -0
  28. package/dist/limbic/limbic_task.js.map +1 -0
  29. package/dist/limbic/limbic_trainer.d.ts +17 -30
  30. package/dist/limbic/limbic_trainer.d.ts.map +1 -1
  31. package/dist/limbic/limbic_trainer.js +38 -144
  32. package/dist/limbic/limbic_trainer.js.map +1 -1
  33. package/dist/ml/classical/ewma.d.ts +32 -0
  34. package/dist/ml/classical/ewma.d.ts.map +1 -0
  35. package/dist/ml/classical/ewma.js +46 -0
  36. package/dist/ml/classical/ewma.js.map +1 -0
  37. package/dist/ml/classical/gbm.d.ts +42 -0
  38. package/dist/ml/classical/gbm.d.ts.map +1 -0
  39. package/dist/ml/classical/gbm.js +116 -0
  40. package/dist/ml/classical/gbm.js.map +1 -0
  41. package/dist/ml/classical/index.d.ts +48 -0
  42. package/dist/ml/classical/index.d.ts.map +1 -0
  43. package/dist/ml/classical/index.js +45 -0
  44. package/dist/ml/classical/index.js.map +1 -0
  45. package/dist/ml/classical/isolation_forest.d.ts +37 -0
  46. package/dist/ml/classical/isolation_forest.d.ts.map +1 -0
  47. package/dist/ml/classical/isolation_forest.js +72 -0
  48. package/dist/ml/classical/isolation_forest.js.map +1 -0
  49. package/dist/ml/classical/kmeans.d.ts +31 -0
  50. package/dist/ml/classical/kmeans.d.ts.map +1 -0
  51. package/dist/ml/classical/kmeans.js +93 -0
  52. package/dist/ml/classical/kmeans.js.map +1 -0
  53. package/dist/ml/classical/knn.d.ts +48 -0
  54. package/dist/ml/classical/knn.d.ts.map +1 -0
  55. package/dist/ml/classical/knn.js +68 -0
  56. package/dist/ml/classical/knn.js.map +1 -0
  57. package/dist/ml/classical/linear.d.ts +29 -0
  58. package/dist/ml/classical/linear.d.ts.map +1 -0
  59. package/dist/ml/classical/linear.js +114 -0
  60. package/dist/ml/classical/linear.js.map +1 -0
  61. package/dist/ml/classical/logistic.d.ts +39 -0
  62. package/dist/ml/classical/logistic.d.ts.map +1 -0
  63. package/dist/ml/classical/logistic.js +103 -0
  64. package/dist/ml/classical/logistic.js.map +1 -0
  65. package/dist/ml/classical/math.d.ts +26 -0
  66. package/dist/ml/classical/math.d.ts.map +1 -0
  67. package/dist/ml/classical/math.js +90 -0
  68. package/dist/ml/classical/math.js.map +1 -0
  69. package/dist/ml/classical/naive_bayes.d.ts +24 -0
  70. package/dist/ml/classical/naive_bayes.d.ts.map +1 -0
  71. package/dist/ml/classical/naive_bayes.js +67 -0
  72. package/dist/ml/classical/naive_bayes.js.map +1 -0
  73. package/dist/ml/classical/robust_z.d.ts +30 -0
  74. package/dist/ml/classical/robust_z.d.ts.map +1 -0
  75. package/dist/ml/classical/robust_z.js +46 -0
  76. package/dist/ml/classical/robust_z.js.map +1 -0
  77. package/dist/ml/dense_head.d.ts +33 -0
  78. package/dist/ml/dense_head.d.ts.map +1 -0
  79. package/dist/ml/dense_head.js +140 -0
  80. package/dist/ml/dense_head.js.map +1 -0
  81. package/dist/ml/features.d.ts +25 -0
  82. package/dist/ml/features.d.ts.map +1 -0
  83. package/dist/ml/features.js +46 -0
  84. package/dist/ml/features.js.map +1 -0
  85. package/dist/ml/federate.d.ts +70 -0
  86. package/dist/ml/federate.d.ts.map +1 -0
  87. package/dist/ml/federate.js +122 -0
  88. package/dist/ml/federate.js.map +1 -0
  89. package/dist/ml/head_trainer.d.ts +76 -0
  90. package/dist/ml/head_trainer.d.ts.map +1 -0
  91. package/dist/ml/head_trainer.js +182 -0
  92. package/dist/ml/head_trainer.js.map +1 -0
  93. package/dist/ml/index.d.ts +23 -0
  94. package/dist/ml/index.d.ts.map +1 -0
  95. package/dist/ml/index.js +11 -0
  96. package/dist/ml/index.js.map +1 -0
  97. package/dist/ml/registry.d.ts +20 -0
  98. package/dist/ml/registry.d.ts.map +1 -0
  99. package/dist/ml/registry.js +43 -0
  100. package/dist/ml/registry.js.map +1 -0
  101. package/dist/ml/run.d.ts +94 -0
  102. package/dist/ml/run.d.ts.map +1 -0
  103. package/dist/ml/run.js +130 -0
  104. package/dist/ml/run.js.map +1 -0
  105. package/dist/ml/tasks/experience.d.ts +90 -0
  106. package/dist/ml/tasks/experience.d.ts.map +1 -0
  107. package/dist/ml/tasks/experience.js +156 -0
  108. package/dist/ml/tasks/experience.js.map +1 -0
  109. package/dist/ml/tasks/index.d.ts +10 -0
  110. package/dist/ml/tasks/index.d.ts.map +1 -0
  111. package/dist/ml/tasks/index.js +28 -0
  112. package/dist/ml/tasks/index.js.map +1 -0
  113. package/dist/ml/tasks/local_success.d.ts +55 -0
  114. package/dist/ml/tasks/local_success.d.ts.map +1 -0
  115. package/dist/ml/tasks/local_success.js +77 -0
  116. package/dist/ml/tasks/local_success.js.map +1 -0
  117. package/dist/ml/tasks/run_anomaly.d.ts +51 -0
  118. package/dist/ml/tasks/run_anomaly.d.ts.map +1 -0
  119. package/dist/ml/tasks/run_anomaly.js +60 -0
  120. package/dist/ml/tasks/run_anomaly.js.map +1 -0
  121. package/dist/ml/train.d.ts +64 -0
  122. package/dist/ml/train.d.ts.map +1 -0
  123. package/dist/ml/train.js +101 -0
  124. package/dist/ml/train.js.map +1 -0
  125. package/dist/ml/types.d.ts +112 -0
  126. package/dist/ml/types.d.ts.map +1 -0
  127. package/dist/ml/types.js +23 -0
  128. package/dist/ml/types.js.map +1 -0
  129. package/dist/moe/moe_model.d.ts.map +1 -1
  130. package/dist/moe/moe_model.js +1 -16
  131. package/dist/moe/moe_model.js.map +1 -1
  132. package/dist/training/cpu_ops.d.ts +2 -0
  133. package/dist/training/cpu_ops.d.ts.map +1 -1
  134. package/dist/training/cpu_ops.js +16 -0
  135. package/dist/training/cpu_ops.js.map +1 -1
  136. package/package.json +1 -1
  137. package/src/evermind/delta_wire.ts +148 -114
  138. package/src/evermind/index.ts +35 -32
  139. package/src/evermind/merge.ts +53 -0
  140. package/src/evermind/package.ts +488 -464
  141. package/src/index.ts +15 -1
  142. package/src/limbic/index.ts +5 -0
  143. package/src/limbic/limbic_task.ts +62 -0
  144. package/src/limbic/limbic_trainer.ts +91 -258
  145. package/src/ml/classical/ewma.ts +68 -0
  146. package/src/ml/classical/gbm.ts +143 -0
  147. package/src/ml/classical/index.ts +76 -0
  148. package/src/ml/classical/isolation_forest.ts +88 -0
  149. package/src/ml/classical/kmeans.ts +102 -0
  150. package/src/ml/classical/knn.ts +98 -0
  151. package/src/ml/classical/linear.ts +119 -0
  152. package/src/ml/classical/logistic.ts +125 -0
  153. package/src/ml/classical/math.ts +93 -0
  154. package/src/ml/classical/naive_bayes.ts +77 -0
  155. package/src/ml/classical/robust_z.ts +65 -0
  156. package/src/ml/dense_head.ts +157 -0
  157. package/src/ml/features.ts +61 -0
  158. package/src/ml/federate.ts +160 -0
  159. package/src/ml/head_trainer.ts +268 -0
  160. package/src/ml/index.ts +57 -0
  161. package/src/ml/registry.ts +44 -0
  162. package/src/ml/run.ts +178 -0
  163. package/src/ml/tasks/experience.ts +214 -0
  164. package/src/ml/tasks/index.ts +30 -0
  165. package/src/ml/tasks/local_success.ts +118 -0
  166. package/src/ml/tasks/run_anomaly.ts +90 -0
  167. package/src/ml/train.ts +136 -0
  168. package/src/ml/types.ts +132 -0
  169. package/src/moe/moe_model.ts +1 -13
  170. package/src/training/cpu_ops.ts +141 -127
@@ -0,0 +1,116 @@
1
+ import { featureDim, sigmoid } from "./math.js";
2
+ function leafValue(rows, lambda) {
3
+ let g = 0;
4
+ let h = 0;
5
+ for (const r of rows) {
6
+ g += r.w * r.g;
7
+ h += r.w * r.h;
8
+ }
9
+ return -g / (h + lambda);
10
+ }
11
+ /** XGBoost-style structure score G²/(H+λ) of a node. */
12
+ function gain(g, h, lambda) {
13
+ return (g * g) / (h + lambda);
14
+ }
15
+ function buildTree(rows, depth, opts) {
16
+ if (depth >= opts.maxDepth || rows.length < 2)
17
+ return { value: leafValue(rows, opts.lambda) };
18
+ let G = 0;
19
+ let H = 0;
20
+ let W = 0;
21
+ for (const r of rows) {
22
+ G += r.w * r.g;
23
+ H += r.w * r.h;
24
+ W += r.w;
25
+ }
26
+ const parent = gain(G, H, opts.lambda);
27
+ let best = null;
28
+ const d = rows[0].x.length;
29
+ for (let f = 0; f < d; f++) {
30
+ const sorted = [...rows].sort((a, b) => a.x[f] - b.x[f]);
31
+ let gl = 0;
32
+ let hl = 0;
33
+ let wl = 0;
34
+ for (let i = 0; i < sorted.length - 1; i++) {
35
+ const r = sorted[i];
36
+ gl += r.w * r.g;
37
+ hl += r.w * r.h;
38
+ wl += r.w;
39
+ const a = r.x[f];
40
+ const b = sorted[i + 1].x[f];
41
+ if (a === b)
42
+ continue;
43
+ if (wl < opts.minLeafWeight || W - wl < opts.minLeafWeight)
44
+ continue;
45
+ const score = gain(gl, hl, opts.lambda) + gain(G - gl, H - hl, opts.lambda) - parent;
46
+ if (score > 1e-12 && (!best || score > best.score))
47
+ best = { feature: f, split: (a + b) / 2, score };
48
+ }
49
+ }
50
+ if (!best)
51
+ return { value: leafValue(rows, opts.lambda) };
52
+ const left = rows.filter((r) => r.x[best.feature] < best.split);
53
+ const right = rows.filter((r) => r.x[best.feature] >= best.split);
54
+ return { feature: best.feature, split: best.split, left: buildTree(left, depth + 1, opts), right: buildTree(right, depth + 1, opts) };
55
+ }
56
+ function treeValue(t, x) {
57
+ while (!("value" in t))
58
+ t = x[t.feature] < t.split ? t.left : t.right;
59
+ return t.value;
60
+ }
61
+ export class GbmModel {
62
+ objective;
63
+ base;
64
+ trees;
65
+ learningRate;
66
+ constructor(objective, base, trees, learningRate) {
67
+ this.objective = objective;
68
+ this.base = base;
69
+ this.trees = trees;
70
+ this.learningRate = learningRate;
71
+ }
72
+ /** The raw additive score (log-odds for `binary`). */
73
+ margin(x) {
74
+ let s = this.base;
75
+ for (const t of this.trees)
76
+ s += this.learningRate * treeValue(t, x);
77
+ return s;
78
+ }
79
+ predict(x) {
80
+ const m = this.margin(x);
81
+ if (this.objective === "regression")
82
+ return { scores: [m], confidence: 1 };
83
+ const p = sigmoid(m);
84
+ return { scores: [1 - p, p], confidence: Math.max(p, 1 - p) };
85
+ }
86
+ }
87
+ export function fitGbm(samples, opts = {}) {
88
+ featureDim(samples.map((s) => s.x));
89
+ const objective = opts.objective ?? "binary";
90
+ const lr = opts.learningRate ?? 0.3;
91
+ const treeOpts = { maxDepth: opts.maxDepth ?? 2, minLeafWeight: opts.minLeafWeight ?? 1, lambda: opts.lambda ?? 1 };
92
+ let wSum = 0;
93
+ let ySum = 0;
94
+ for (const s of samples) {
95
+ wSum += s.weight ?? 1;
96
+ ySum += (s.weight ?? 1) * s.y;
97
+ }
98
+ const yMean = ySum / wSum;
99
+ const base = objective === "binary" ? Math.log(Math.max(yMean, 1e-6) / Math.max(1 - yMean, 1e-6)) : yMean;
100
+ const margins = samples.map(() => base);
101
+ const trees = [];
102
+ for (let t = 0; t < (opts.trees ?? 50); t++) {
103
+ const rows = samples.map((s, i) => {
104
+ if (objective === "binary") {
105
+ const p = sigmoid(margins[i]);
106
+ return { x: s.x, g: p - s.y, h: Math.max(p * (1 - p), 1e-6), w: s.weight ?? 1 };
107
+ }
108
+ return { x: s.x, g: margins[i] - s.y, h: 1, w: s.weight ?? 1 };
109
+ });
110
+ const tree = buildTree(rows, 0, treeOpts);
111
+ trees.push(tree);
112
+ samples.forEach((s, i) => (margins[i] = margins[i] + lr * treeValue(tree, s.x)));
113
+ }
114
+ return new GbmModel(objective, base, trees, lr);
115
+ }
116
+ //# sourceMappingURL=gbm.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"gbm.js","sourceRoot":"","sources":["../../../src/ml/classical/gbm.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,48 @@
1
+ /**
2
+ * ml/classical — pure-TypeScript algorithms, one file each, and the ONE dispatch
3
+ * from a {@link ClassicalAlgorithm} name to its fit.
4
+ */
5
+ import type { ClassicalAlgorithm, MlPredictor, MlSample } from "../types.js";
6
+ import { type KnnOptions } from "./knn.js";
7
+ import { type NaiveBayesOptions } from "./naive_bayes.js";
8
+ import { type LogisticOptions } from "./logistic.js";
9
+ import { type LinearOptions } from "./linear.js";
10
+ import { type KMeansOptions } from "./kmeans.js";
11
+ import { type RobustZOptions } from "./robust_z.js";
12
+ import { type EwmaOptions } from "./ewma.js";
13
+ import { type IsolationForestOptions } from "./isolation_forest.js";
14
+ import { type GbmOptions } from "./gbm.js";
15
+ export { KnnModel, fitKnn } from "./knn.js";
16
+ export type { KnnOptions, KnnMetric, Neighbour } from "./knn.js";
17
+ export { NaiveBayesModel, fitNaiveBayes } from "./naive_bayes.js";
18
+ export type { NaiveBayesOptions } from "./naive_bayes.js";
19
+ export { LogisticModel, fitLogistic } from "./logistic.js";
20
+ export type { LogisticOptions } from "./logistic.js";
21
+ export { LinearModel, fitLinear, solveLinearSystem } from "./linear.js";
22
+ export type { LinearOptions } from "./linear.js";
23
+ export { KMeansModel, fitKMeans } from "./kmeans.js";
24
+ export type { KMeansOptions } from "./kmeans.js";
25
+ export { RobustZModel, fitRobustZ, anomalyConfidence } from "./robust_z.js";
26
+ export type { RobustZOptions } from "./robust_z.js";
27
+ export { EwmaModel, fitEwma } from "./ewma.js";
28
+ export type { EwmaOptions } from "./ewma.js";
29
+ export { IsolationForestModel, fitIsolationForest } from "./isolation_forest.js";
30
+ export type { IsolationForestOptions } from "./isolation_forest.js";
31
+ export { GbmModel, fitGbm } from "./gbm.js";
32
+ export type { GbmOptions, GbmObjective } from "./gbm.js";
33
+ export { cosine, dot } from "./math.js";
34
+ /** Per-algorithm options, keyed by algorithm name. */
35
+ export interface ClassicalOptions {
36
+ knn?: KnnOptions;
37
+ "naive-bayes"?: NaiveBayesOptions;
38
+ logistic?: LogisticOptions;
39
+ linear?: LinearOptions;
40
+ kmeans?: KMeansOptions;
41
+ "robust-z"?: RobustZOptions;
42
+ ewma?: EwmaOptions;
43
+ "isolation-forest"?: IsolationForestOptions;
44
+ "gbm-small"?: GbmOptions;
45
+ }
46
+ /** Fit `algorithm` on `samples`. Unsupervised algorithms ignore `y`. */
47
+ export declare function fitClassical(algorithm: ClassicalAlgorithm, samples: readonly MlSample[], opts?: ClassicalOptions): MlPredictor;
48
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/ml/classical/index.ts"],"names":[],"mappings":"AAAA;;;GAGG;AACH,OAAO,KAAK,EAAE,kBAAkB,EAAE,WAAW,EAAE,QAAQ,EAAE,MAAM,aAAa,CAAC;AAC7E,OAAO,EAAU,KAAK,UAAU,EAAE,MAAM,UAAU,CAAC;AACnD,OAAO,EAAiB,KAAK,iBAAiB,EAAE,MAAM,kBAAkB,CAAC;AACzE,OAAO,EAAe,KAAK,eAAe,EAAE,MAAM,eAAe,CAAC;AAClE,OAAO,EAAa,KAAK,aAAa,EAAE,MAAM,aAAa,CAAC;AAC5D,OAAO,EAAa,KAAK,aAAa,EAAE,MAAM,aAAa,CAAC;AAC5D,OAAO,EAAc,KAAK,cAAc,EAAE,MAAM,eAAe,CAAC;AAChE,OAAO,EAAW,KAAK,WAAW,EAAE,MAAM,WAAW,CAAC;AACtD,OAAO,EAAsB,KAAK,sBAAsB,EAAE,MAAM,uBAAuB,CAAC;AACxF,OAAO,EAAU,KAAK,UAAU,EAAE,MAAM,UAAU,CAAC;AAEnD,OAAO,EAAE,QAAQ,EAAE,MAAM,EAAE,MAAM,UAAU,CAAC;AAC5C,YAAY,EAAE,UAAU,EAAE,SAAS,EAAE,SAAS,EAAE,MAAM,UAAU,CAAC;AACjE,OAAO,EAAE,eAAe,EAAE,aAAa,EAAE,MAAM,kBAAkB,CAAC;AAClE,YAAY,EAAE,iBAAiB,EAAE,MAAM,kBAAkB,CAAC;AAC1D,OAAO,EAAE,aAAa,EAAE,WAAW,EAAE,MAAM,eAAe,CAAC;AAC3D,YAAY,EAAE,eAAe,EAAE,MAAM,eAAe,CAAC;AACrD,OAAO,EAAE,WAAW,EAAE,SAAS,EAAE,iBAAiB,EAAE,MAAM,aAAa,CAAC;AACxE,YAAY,EAAE,aAAa,EAAE,MAAM,aAAa,CAAC;AACjD,OAAO,EAAE,WAAW,EAAE,SAAS,EAAE,MAAM,aAAa,CAAC;AACrD,YAAY,EAAE,aAAa,EAAE,MAAM,aAAa,CAAC;AACjD,OAAO,EAAE,YAAY,EAAE,UAAU,EAAE,iBAAiB,EAAE,MAAM,eAAe,CAAC;AAC5E,YAAY,EAAE,cAAc,EAAE,MAAM,eAAe,CAAC;AACpD,OAAO,EAAE,SAAS,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AAC/C,YAAY,EAAE,WAAW,EAAE,MAAM,WAAW,CAAC;AAC7C,OAAO,EAAE,oBAAoB,EAAE,kBAAkB,EAAE,MAAM,uBAAuB,CAAC;AACjF,YAAY,EAAE,sBAAsB,EAAE,MAAM,uBAAuB,CAAC;AACpE,OAAO,EAAE,QAAQ,EAAE,MAAM,EAAE,MAAM,UAAU,CAAC;AAC5C,YAAY,EAAE,UAAU,EAAE,YAAY,EAAE,MAAM,UAAU,CAAC;AACzD,OAAO,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,WAAW,CAAC;AAExC,sDAAsD;AACtD,MAAM,WAAW,gBAAgB;IAC/B,GAAG,CAAC,EAAE,UAAU,CAAC;IACjB,aAAa,CAAC,EAAE,iBAAiB,CAAC;IAClC,QAAQ,CAAC,EAAE,eAAe,CAAC;IAC3B,MAAM,CAAC,EAAE,aAAa,CAAC;IACvB,MAAM,CAAC,EAAE,aAAa,CAAC;IACvB,UAAU,CAAC,EAAE,cAAc,CAAC;IAC5B,IAAI,CAAC,EAAE,WAAW,CAAC;IACnB,kBAAkB,CAAC,EAAE,sBAAsB,CAAC;IAC5C,WAAW,CAAC,EAAE,UAAU,CAAC;CAC1B;AAED,wEAAwE;AACxE,wBAAgB,YAAY,CAC1B,SAAS,EAAE,kBAAkB,EAC7B,OAAO,EAAE,SAAS,QAAQ,EAAE,EAC5B,IAAI,GAAE,gBAAqB,GAC1B,WAAW,CAsBb"}
@@ -0,0 +1,45 @@
1
+ import { fitKnn } from "./knn.js";
2
+ import { fitNaiveBayes } from "./naive_bayes.js";
3
+ import { fitLogistic } from "./logistic.js";
4
+ import { fitLinear } from "./linear.js";
5
+ import { fitKMeans } from "./kmeans.js";
6
+ import { fitRobustZ } from "./robust_z.js";
7
+ import { fitEwma } from "./ewma.js";
8
+ import { fitIsolationForest } from "./isolation_forest.js";
9
+ import { fitGbm } from "./gbm.js";
10
+ export { KnnModel, fitKnn } from "./knn.js";
11
+ export { NaiveBayesModel, fitNaiveBayes } from "./naive_bayes.js";
12
+ export { LogisticModel, fitLogistic } from "./logistic.js";
13
+ export { LinearModel, fitLinear, solveLinearSystem } from "./linear.js";
14
+ export { KMeansModel, fitKMeans } from "./kmeans.js";
15
+ export { RobustZModel, fitRobustZ, anomalyConfidence } from "./robust_z.js";
16
+ export { EwmaModel, fitEwma } from "./ewma.js";
17
+ export { IsolationForestModel, fitIsolationForest } from "./isolation_forest.js";
18
+ export { GbmModel, fitGbm } from "./gbm.js";
19
+ export { cosine, dot } from "./math.js";
20
+ /** Fit `algorithm` on `samples`. Unsupervised algorithms ignore `y`. */
21
+ export function fitClassical(algorithm, samples, opts = {}) {
22
+ if (samples.length === 0)
23
+ throw new Error(`fitClassical(${algorithm}): no samples`);
24
+ switch (algorithm) {
25
+ case "knn":
26
+ return fitKnn(samples, opts.knn);
27
+ case "naive-bayes":
28
+ return fitNaiveBayes(samples, opts["naive-bayes"]);
29
+ case "logistic":
30
+ return fitLogistic(samples, opts.logistic);
31
+ case "linear":
32
+ return fitLinear(samples, opts.linear);
33
+ case "kmeans":
34
+ return fitKMeans(samples, opts.kmeans);
35
+ case "robust-z":
36
+ return fitRobustZ(samples, opts["robust-z"]);
37
+ case "ewma":
38
+ return fitEwma(samples, opts.ewma);
39
+ case "isolation-forest":
40
+ return fitIsolationForest(samples, opts["isolation-forest"]);
41
+ case "gbm-small":
42
+ return fitGbm(samples, opts["gbm-small"]);
43
+ }
44
+ }
45
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/ml/classical/index.ts"],"names":[],"mappings":"AAKA,OAAO,EAAE,MAAM,EAAmB,MAAM,UAAU,CAAC;AACnD,OAAO,EAAE,aAAa,EAA0B,MAAM,kBAAkB,CAAC;AACzE,OAAO,EAAE,WAAW,EAAwB,MAAM,eAAe,CAAC;AAClE,OAAO,EAAE,SAAS,EAAsB,MAAM,aAAa,CAAC;AAC5D,OAAO,EAAE,SAAS,EAAsB,MAAM,aAAa,CAAC;AAC5D,OAAO,EAAE,UAAU,EAAuB,MAAM,eAAe,CAAC;AAChE,OAAO,EAAE,OAAO,EAAoB,MAAM,WAAW,CAAC;AACtD,OAAO,EAAE,kBAAkB,EAA+B,MAAM,uBAAuB,CAAC;AACxF,OAAO,EAAE,MAAM,EAAmB,MAAM,UAAU,CAAC;AAEnD,OAAO,EAAE,QAAQ,EAAE,MAAM,EAAE,MAAM,UAAU,CAAC;AAE5C,OAAO,EAAE,eAAe,EAAE,aAAa,EAAE,MAAM,kBAAkB,CAAC;AAElE,OAAO,EAAE,aAAa,EAAE,WAAW,EAAE,MAAM,eAAe,CAAC;AAE3D,OAAO,EAAE,WAAW,EAAE,SAAS,EAAE,iBAAiB,EAAE,MAAM,aAAa,CAAC;AAExE,OAAO,EAAE,WAAW,EAAE,SAAS,EAAE,MAAM,aAAa,CAAC;AAErD,OAAO,EAAE,YAAY,EAAE,UAAU,EAAE,iBAAiB,EAAE,MAAM,eAAe,CAAC;AAE5E,OAAO,EAAE,SAAS,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AAE/C,OAAO,EAAE,oBAAoB,EAAE,kBAAkB,EAAE,MAAM,uBAAuB,CAAC;AAEjF,OAAO,EAAE,QAAQ,EAAE,MAAM,EAAE,MAAM,UAAU,CAAC;AAE5C,OAAO,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,WAAW,CAAC;AAexC,wEAAwE;AACxE,MAAM,UAAU,YAAY,CAC1B,SAA6B,EAC7B,OAA4B,EAC5B,OAAyB,EAAE;IAE3B,IAAI,OAAO,CAAC,MAAM,KAAK,CAAC;QAAE,MAAM,IAAI,KAAK,CAAC,gBAAgB,SAAS,eAAe,CAAC,CAAC;IACpF,QAAQ,SAAS,EAAE,CAAC;QAClB,KAAK,KAAK;YACR,OAAO,MAAM,CAAC,OAAO,EAAE,IAAI,CAAC,GAAG,CAAC,CAAC;QACnC,KAAK,aAAa;YAChB,OAAO,aAAa,CAAC,OAAO,EAAE,IAAI,CAAC,aAAa,CAAC,CAAC,CAAC;QACrD,KAAK,UAAU;YACb,OAAO,WAAW,CAAC,OAAO,EAAE,IAAI,CAAC,QAAQ,CAAC,CAAC;QAC7C,KAAK,QAAQ;YACX,OAAO,SAAS,CAAC,OAAO,EAAE,IAAI,CAAC,MAAM,CAAC,CAAC;QACzC,KAAK,QAAQ;YACX,OAAO,SAAS,CAAC,OAAO,EAAE,IAAI,CAAC,MAAM,CAAC,CAAC;QACzC,KAAK,UAAU;YACb,OAAO,UAAU,CAAC,OAAO,EAAE,IAAI,CAAC,UAAU,CAAC,CAAC,CAAC;QAC/C,KAAK,MAAM;YACT,OAAO,OAAO,CAAC,OAAO,EAAE,IAAI,CAAC,IAAI,CAAC,CAAC;QACrC,KAAK,kBAAkB;YACrB,OAAO,kBAAkB,CAAC,OAAO,EAAE,IAAI,CAAC,kBAAkB,CAAC,CAAC,CAAC;QAC/D,KAAK,WAAW;YACd,OAAO,MAAM,CAAC,OAAO,EAAE,IAAI,CAAC,WAAW,CAAC,CAAC,CAAC;IAC9C,CAAC;AACH,CAAC"}
@@ -0,0 +1,37 @@
1
+ /**
2
+ * ml/classical/isolation_forest.ts — Isolation Forest (Liu, Ting & Zhou 2008).
3
+ *
4
+ * Anomalies are few and different, so random axis-aligned splits isolate them in
5
+ * fewer steps. Score s(x) = 2^(−E[h(x)] / c(ψ)): near 1 = anomalous, ≤ 0.5 =
6
+ * normal. Prediction: `scores[0] = s / threshold` — ≥ 1 is anomalous.
7
+ */
8
+ import type { MlPrediction, MlPredictor, MlSample } from "../types.js";
9
+ import { type Vec } from "./math.js";
10
+ export interface IsolationForestOptions {
11
+ trees?: number;
12
+ /** Subsample size ψ per tree. Default min(256, n). */
13
+ sampleSize?: number;
14
+ /** Raw score at which a point is anomalous. Default 0.6. */
15
+ threshold?: number;
16
+ seed?: number;
17
+ }
18
+ type ITree = {
19
+ size: number;
20
+ } | {
21
+ feature: number;
22
+ split: number;
23
+ left: ITree;
24
+ right: ITree;
25
+ };
26
+ export declare class IsolationForestModel implements MlPredictor {
27
+ readonly trees: readonly ITree[];
28
+ readonly sampleSize: number;
29
+ readonly threshold: number;
30
+ constructor(trees: readonly ITree[], sampleSize: number, threshold: number);
31
+ /** The raw isolation score in (0, 1]. */
32
+ score(x: Vec): number;
33
+ predict(x: Float32Array): MlPrediction;
34
+ }
35
+ export declare function fitIsolationForest(samples: readonly MlSample[], opts?: IsolationForestOptions): IsolationForestModel;
36
+ export {};
37
+ //# sourceMappingURL=isolation_forest.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"isolation_forest.d.ts","sourceRoot":"","sources":["../../../src/ml/classical/isolation_forest.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AACH,OAAO,KAAK,EAAE,YAAY,EAAE,WAAW,EAAE,QAAQ,EAAE,MAAM,aAAa,CAAC;AACvE,OAAO,EAAgD,KAAK,GAAG,EAAE,MAAM,WAAW,CAAC;AAGnF,MAAM,WAAW,sBAAsB;IACrC,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,sDAAsD;IACtD,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,4DAA4D;IAC5D,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,IAAI,CAAC,EAAE,MAAM,CAAC;CACf;AAED,KAAK,KAAK,GAAG;IAAE,IAAI,EAAE,MAAM,CAAA;CAAE,GAAG;IAAE,OAAO,EAAE,MAAM,CAAC;IAAC,KAAK,EAAE,MAAM,CAAC;IAAC,IAAI,EAAE,KAAK,CAAC;IAAC,KAAK,EAAE,KAAK,CAAA;CAAE,CAAC;AA6B9F,qBAAa,oBAAqB,YAAW,WAAW;IAEpD,QAAQ,CAAC,KAAK,EAAE,SAAS,KAAK,EAAE;IAChC,QAAQ,CAAC,UAAU,EAAE,MAAM;IAC3B,QAAQ,CAAC,SAAS,EAAE,MAAM;gBAFjB,KAAK,EAAE,SAAS,KAAK,EAAE,EACvB,UAAU,EAAE,MAAM,EAClB,SAAS,EAAE,MAAM;IAG5B,yCAAyC;IACzC,KAAK,CAAC,CAAC,EAAE,GAAG,GAAG,MAAM;IAOrB,OAAO,CAAC,CAAC,EAAE,YAAY,GAAG,YAAY;CAIvC;AAED,wBAAgB,kBAAkB,CAAC,OAAO,EAAE,SAAS,QAAQ,EAAE,EAAE,IAAI,GAAE,sBAA2B,GAAG,oBAAoB,CAiBxH"}
@@ -0,0 +1,72 @@
1
+ import { averagePathLength, featureDim, seededUniform } from "./math.js";
2
+ import { anomalyConfidence } from "./robust_z.js";
3
+ function buildTree(X, depth, limit, rnd) {
4
+ if (depth >= limit || X.length <= 1)
5
+ return { size: X.length };
6
+ const d = X[0].length;
7
+ // Only features that still vary can split; none left = an isolated leaf.
8
+ const varying = [];
9
+ for (let f = 0; f < d; f++) {
10
+ let lo = Infinity;
11
+ let hi = -Infinity;
12
+ for (const x of X) {
13
+ lo = Math.min(lo, x[f]);
14
+ hi = Math.max(hi, x[f]);
15
+ }
16
+ if (hi > lo)
17
+ varying.push({ f, lo, hi });
18
+ }
19
+ if (varying.length === 0)
20
+ return { size: X.length };
21
+ const { f, lo, hi } = varying[Math.floor(rnd() * varying.length)];
22
+ const split = lo + rnd() * (hi - lo);
23
+ const left = X.filter((x) => x[f] < split);
24
+ const right = X.filter((x) => x[f] >= split);
25
+ return { feature: f, split, left: buildTree(left, depth + 1, limit, rnd), right: buildTree(right, depth + 1, limit, rnd) };
26
+ }
27
+ function pathLength(tree, x, depth = 0) {
28
+ if ("size" in tree)
29
+ return depth + averagePathLength(tree.size);
30
+ return pathLength(x[tree.feature] < tree.split ? tree.left : tree.right, x, depth + 1);
31
+ }
32
+ export class IsolationForestModel {
33
+ trees;
34
+ sampleSize;
35
+ threshold;
36
+ constructor(trees, sampleSize, threshold) {
37
+ this.trees = trees;
38
+ this.sampleSize = sampleSize;
39
+ this.threshold = threshold;
40
+ }
41
+ /** The raw isolation score in (0, 1]. */
42
+ score(x) {
43
+ const c = averagePathLength(this.sampleSize);
44
+ if (c === 0)
45
+ return 0.5;
46
+ const mean = this.trees.reduce((s, t) => s + pathLength(t, x), 0) / this.trees.length;
47
+ return Math.pow(2, -mean / c);
48
+ }
49
+ predict(x) {
50
+ const s = this.score(x) / this.threshold;
51
+ return { scores: [s], confidence: anomalyConfidence(s) };
52
+ }
53
+ }
54
+ export function fitIsolationForest(samples, opts = {}) {
55
+ const X = samples.map((s) => s.x);
56
+ featureDim(X);
57
+ const rnd = seededUniform(opts.seed ?? 0x15f0);
58
+ const psi = Math.min(opts.sampleSize ?? 256, X.length);
59
+ const limit = Math.ceil(Math.log2(Math.max(psi, 2)));
60
+ const trees = [];
61
+ for (let t = 0; t < (opts.trees ?? 100); t++) {
62
+ // Sample ψ points without replacement (partial Fisher–Yates over indices).
63
+ const idx = X.map((_, i) => i);
64
+ for (let i = 0; i < psi; i++) {
65
+ const j = i + Math.floor(rnd() * (idx.length - i));
66
+ [idx[i], idx[j]] = [idx[j], idx[i]];
67
+ }
68
+ trees.push(buildTree(idx.slice(0, psi).map((i) => X[i]), 0, limit, rnd));
69
+ }
70
+ return new IsolationForestModel(trees, psi, opts.threshold ?? 0.6);
71
+ }
72
+ //# sourceMappingURL=isolation_forest.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"isolation_forest.js","sourceRoot":"","sources":["../../../src/ml/classical/isolation_forest.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,31 @@
1
+ /**
2
+ * ml/classical/kmeans.ts — k-means clustering (k-means++ seeding, Lloyd iterations).
3
+ *
4
+ * Deterministic for a given seed. A prediction is the nearest centroid; its
5
+ * confidence is how much closer that centroid is than the runner-up.
6
+ */
7
+ import type { MlPrediction, MlPredictor, MlSample } from "../types.js";
8
+ import { type Vec } from "./math.js";
9
+ export interface KMeansOptions {
10
+ /** Clusters. Default round(√(n/2)), at least 1. */
11
+ k?: number;
12
+ maxIterations?: number;
13
+ seed?: number;
14
+ }
15
+ export declare class KMeansModel implements MlPredictor {
16
+ readonly centroids: Float32Array[];
17
+ /** Sum of squared distances of the fitted points to their centroid. */
18
+ readonly inertia: number;
19
+ constructor(centroids: Float32Array[],
20
+ /** Sum of squared distances of the fitted points to their centroid. */
21
+ inertia: number);
22
+ /** Nearest centroid index and the two smallest squared distances. */
23
+ assign(x: Vec): {
24
+ cluster: number;
25
+ d1: number;
26
+ d2: number;
27
+ };
28
+ predict(x: Float32Array): MlPrediction;
29
+ }
30
+ export declare function fitKMeans(samples: readonly MlSample[], opts?: KMeansOptions): KMeansModel;
31
+ //# sourceMappingURL=kmeans.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"kmeans.d.ts","sourceRoot":"","sources":["../../../src/ml/classical/kmeans.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AACH,OAAO,KAAK,EAAE,YAAY,EAAE,WAAW,EAAE,QAAQ,EAAE,MAAM,aAAa,CAAC;AACvE,OAAO,EAA8C,KAAK,GAAG,EAAE,MAAM,WAAW,CAAC;AAEjF,MAAM,WAAW,aAAa;IAC5B,mDAAmD;IACnD,CAAC,CAAC,EAAE,MAAM,CAAC;IACX,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,IAAI,CAAC,EAAE,MAAM,CAAC;CACf;AAED,qBAAa,WAAY,YAAW,WAAW;IAE3C,QAAQ,CAAC,SAAS,EAAE,YAAY,EAAE;IAClC,uEAAuE;IACvE,QAAQ,CAAC,OAAO,EAAE,MAAM;gBAFf,SAAS,EAAE,YAAY,EAAE;IAClC,uEAAuE;IAC9D,OAAO,EAAE,MAAM;IAG1B,qEAAqE;IACrE,MAAM,CAAC,CAAC,EAAE,GAAG,GAAG;QAAE,OAAO,EAAE,MAAM,CAAC;QAAC,EAAE,EAAE,MAAM,CAAC;QAAC,EAAE,EAAE,MAAM,CAAA;KAAE;IAe3D,OAAO,CAAC,CAAC,EAAE,YAAY,GAAG,YAAY;CAKvC;AAED,wBAAgB,SAAS,CAAC,OAAO,EAAE,SAAS,QAAQ,EAAE,EAAE,IAAI,GAAE,aAAkB,GAAG,WAAW,CAuD7F"}
@@ -0,0 +1,93 @@
1
+ import { featureDim, seededUniform, squaredDistance } from "./math.js";
2
+ export class KMeansModel {
3
+ centroids;
4
+ inertia;
5
+ constructor(centroids,
6
+ /** Sum of squared distances of the fitted points to their centroid. */
7
+ inertia) {
8
+ this.centroids = centroids;
9
+ this.inertia = inertia;
10
+ }
11
+ /** Nearest centroid index and the two smallest squared distances. */
12
+ assign(x) {
13
+ let cluster = 0;
14
+ let d1 = Infinity;
15
+ let d2 = Infinity;
16
+ this.centroids.forEach((c, i) => {
17
+ const d = squaredDistance(x, c);
18
+ if (d < d1) {
19
+ d2 = d1;
20
+ d1 = d;
21
+ cluster = i;
22
+ }
23
+ else if (d < d2)
24
+ d2 = d;
25
+ });
26
+ return { cluster, d1, d2 };
27
+ }
28
+ predict(x) {
29
+ const { cluster, d1, d2 } = this.assign(x);
30
+ const confidence = Number.isFinite(d2) && d2 > 0 ? 1 - Math.sqrt(d1) / Math.sqrt(d2) : 1;
31
+ return { scores: [cluster], confidence: Math.max(0, Math.min(1, confidence)) };
32
+ }
33
+ }
34
+ export function fitKMeans(samples, opts = {}) {
35
+ const X = samples.map((s) => s.x);
36
+ const d = featureDim(X);
37
+ const k = Math.min(X.length, Math.max(1, opts.k ?? Math.round(Math.sqrt(X.length / 2))));
38
+ const rnd = seededUniform(opts.seed ?? 0x6b6d);
39
+ // k-means++: first centroid uniformly, the rest ∝ squared distance to the nearest chosen one.
40
+ const centroids = [Float32Array.from(X[Math.floor(rnd() * X.length)])];
41
+ const nearest = X.map((x) => squaredDistance(x, centroids[0]));
42
+ while (centroids.length < k) {
43
+ const total = nearest.reduce((a, b) => a + b, 0);
44
+ let pick = 0;
45
+ if (total > 0) {
46
+ let r = rnd() * total;
47
+ for (pick = 0; pick < X.length - 1; pick++) {
48
+ r -= nearest[pick];
49
+ if (r <= 0)
50
+ break;
51
+ }
52
+ }
53
+ else {
54
+ pick = centroids.length; // every point coincides with a centroid; take the next index
55
+ }
56
+ const c = Float32Array.from(X[pick]);
57
+ centroids.push(c);
58
+ X.forEach((x, i) => (nearest[i] = Math.min(nearest[i], squaredDistance(x, c))));
59
+ }
60
+ const assign = new Int32Array(X.length).fill(-1);
61
+ const maxIt = opts.maxIterations ?? 100;
62
+ for (let it = 0; it < maxIt; it++) {
63
+ let changed = false;
64
+ const model = new KMeansModel(centroids, 0);
65
+ X.forEach((x, i) => {
66
+ const c = model.assign(x).cluster;
67
+ if (assign[i] !== c) {
68
+ assign[i] = c;
69
+ changed = true;
70
+ }
71
+ });
72
+ if (!changed)
73
+ break;
74
+ const sums = centroids.map(() => new Float64Array(d));
75
+ const counts = new Array(k).fill(0);
76
+ X.forEach((x, i) => {
77
+ const c = assign[i];
78
+ counts[c] = counts[c] + 1;
79
+ for (let j = 0; j < d; j++)
80
+ sums[c][j] = sums[c][j] + x[j];
81
+ });
82
+ // An emptied cluster keeps its previous centroid.
83
+ centroids.forEach((c, ci) => {
84
+ if (counts[ci] > 0)
85
+ for (let j = 0; j < d; j++)
86
+ c[j] = sums[ci][j] / counts[ci];
87
+ });
88
+ }
89
+ let inertia = 0;
90
+ X.forEach((x, i) => (inertia += squaredDistance(x, centroids[assign[i]])));
91
+ return new KMeansModel(centroids, inertia);
92
+ }
93
+ //# sourceMappingURL=kmeans.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"kmeans.js","sourceRoot":"","sources":["../../../src/ml/classical/kmeans.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,48 @@
1
+ /**
2
+ * ml/classical/knn.ts — k-nearest-neighbours classification over feature vectors.
3
+ *
4
+ * Votes are similarity-weighted (cosine similarity, or 1/(1+distance) for the
5
+ * euclidean metric), so a close neighbour counts for more than a far one. The
6
+ * same index answers "what is my nearest neighbour?" — the de-duplication query.
7
+ */
8
+ import type { MlPrediction, MlPredictor, MlSample } from "../types.js";
9
+ import { type Vec } from "./math.js";
10
+ export type KnnMetric = "cosine" | "euclidean";
11
+ export interface KnnOptions {
12
+ /** Neighbours that vote. Default 5 (capped at the sample count). */
13
+ k?: number;
14
+ metric?: KnnMetric;
15
+ /** Number of classes (default: inferred from the labels, at least 2). */
16
+ classes?: number;
17
+ }
18
+ export interface Neighbour {
19
+ index: number;
20
+ /** Higher = closer: cosine similarity, or 1/(1+distance) for euclidean. */
21
+ similarity: number;
22
+ }
23
+ export declare class KnnModel implements MlPredictor {
24
+ readonly k: number;
25
+ readonly metric: KnnMetric;
26
+ readonly classes: number;
27
+ private readonly _x;
28
+ private readonly _y;
29
+ private readonly _w;
30
+ constructor(k: number, metric: KnnMetric, classes: number);
31
+ /** How many points the index holds. */
32
+ get size(): number;
33
+ /** Add one labelled point (online — the index never needs a refit). */
34
+ add(x: Vec, y?: number, weight?: number): void;
35
+ similarity(a: Vec, b: Vec): number;
36
+ /** The `k` closest points, closest first. */
37
+ neighbours(x: Vec, k?: number): Neighbour[];
38
+ /** The single closest point, or null when the index is empty. */
39
+ nearest(x: Vec): Neighbour | null;
40
+ /** The label of an indexed point. */
41
+ labelOf(index: number): number;
42
+ /** Class probabilities from similarity-weighted votes (uniform when empty). */
43
+ proba(x: Vec): number[];
44
+ predict(x: Float32Array): MlPrediction;
45
+ }
46
+ /** Index `samples` for kNN classification. */
47
+ export declare function fitKnn(samples: readonly MlSample[], opts?: KnnOptions): KnnModel;
48
+ //# sourceMappingURL=knn.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"knn.d.ts","sourceRoot":"","sources":["../../../src/ml/classical/knn.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AACH,OAAO,KAAK,EAAE,YAAY,EAAE,WAAW,EAAE,QAAQ,EAAE,MAAM,aAAa,CAAC;AACvE,OAAO,EAAmE,KAAK,GAAG,EAAE,MAAM,WAAW,CAAC;AAEtG,MAAM,MAAM,SAAS,GAAG,QAAQ,GAAG,WAAW,CAAC;AAE/C,MAAM,WAAW,UAAU;IACzB,oEAAoE;IACpE,CAAC,CAAC,EAAE,MAAM,CAAC;IACX,MAAM,CAAC,EAAE,SAAS,CAAC;IACnB,yEAAyE;IACzE,OAAO,CAAC,EAAE,MAAM,CAAC;CAClB;AAED,MAAM,WAAW,SAAS;IACxB,KAAK,EAAE,MAAM,CAAC;IACd,2EAA2E;IAC3E,UAAU,EAAE,MAAM,CAAC;CACpB;AAED,qBAAa,QAAS,YAAW,WAAW;IAMxC,QAAQ,CAAC,CAAC,EAAE,MAAM;IAClB,QAAQ,CAAC,MAAM,EAAE,SAAS;IAC1B,QAAQ,CAAC,OAAO,EAAE,MAAM;IAP1B,OAAO,CAAC,QAAQ,CAAC,EAAE,CAAsB;IACzC,OAAO,CAAC,QAAQ,CAAC,EAAE,CAAgB;IACnC,OAAO,CAAC,QAAQ,CAAC,EAAE,CAAgB;gBAGxB,CAAC,EAAE,MAAM,EACT,MAAM,EAAE,SAAS,EACjB,OAAO,EAAE,MAAM;IAK1B,uCAAuC;IACvC,IAAI,IAAI,IAAI,MAAM,CAEjB;IAED,uEAAuE;IACvE,GAAG,CAAC,CAAC,EAAE,GAAG,EAAE,CAAC,SAAI,EAAE,MAAM,SAAI,GAAG,IAAI;IAMpC,UAAU,CAAC,CAAC,EAAE,GAAG,EAAE,CAAC,EAAE,GAAG,GAAG,MAAM;IAIlC,6CAA6C;IAC7C,UAAU,CAAC,CAAC,EAAE,GAAG,EAAE,CAAC,GAAE,MAAe,GAAG,SAAS,EAAE;IAMnD,iEAAiE;IACjE,OAAO,CAAC,CAAC,EAAE,GAAG,GAAG,SAAS,GAAG,IAAI;IAIjC,qCAAqC;IACrC,OAAO,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM;IAI9B,+EAA+E;IAC/E,KAAK,CAAC,CAAC,EAAE,GAAG,GAAG,MAAM,EAAE;IAWvB,OAAO,CAAC,CAAC,EAAE,YAAY,GAAG,YAAY;CAIvC;AAED,8CAA8C;AAC9C,wBAAgB,MAAM,CAAC,OAAO,EAAE,SAAS,QAAQ,EAAE,EAAE,IAAI,GAAE,UAAe,GAAG,QAAQ,CAMpF"}
@@ -0,0 +1,68 @@
1
+ import { classCount, cosine, featureDim, squaredDistance, topProbability } from "./math.js";
2
+ export class KnnModel {
3
+ k;
4
+ metric;
5
+ classes;
6
+ _x = [];
7
+ _y = [];
8
+ _w = [];
9
+ constructor(k, metric, classes) {
10
+ this.k = k;
11
+ this.metric = metric;
12
+ this.classes = classes;
13
+ if (!(k >= 1))
14
+ throw new Error(`KnnModel: k must be ≥ 1 (got ${k})`);
15
+ }
16
+ /** How many points the index holds. */
17
+ get size() {
18
+ return this._x.length;
19
+ }
20
+ /** Add one labelled point (online — the index never needs a refit). */
21
+ add(x, y = 0, weight = 1) {
22
+ this._x.push(Float32Array.from(x));
23
+ this._y.push(y);
24
+ this._w.push(weight);
25
+ }
26
+ similarity(a, b) {
27
+ return this.metric === "cosine" ? cosine(a, b) : 1 / (1 + Math.sqrt(squaredDistance(a, b)));
28
+ }
29
+ /** The `k` closest points, closest first. */
30
+ neighbours(x, k = this.k) {
31
+ const all = this._x.map((p, index) => ({ index, similarity: this.similarity(x, p) }));
32
+ all.sort((a, b) => b.similarity - a.similarity || a.index - b.index);
33
+ return all.slice(0, Math.min(k, all.length));
34
+ }
35
+ /** The single closest point, or null when the index is empty. */
36
+ nearest(x) {
37
+ return this.neighbours(x, 1)[0] ?? null;
38
+ }
39
+ /** The label of an indexed point. */
40
+ labelOf(index) {
41
+ return this._y[index];
42
+ }
43
+ /** Class probabilities from similarity-weighted votes (uniform when empty). */
44
+ proba(x) {
45
+ const votes = new Array(this.classes).fill(0);
46
+ for (const n of this.neighbours(x)) {
47
+ // Shift cosine into (0, 2] so an orthogonal neighbour still casts a small vote.
48
+ const w = (this.metric === "cosine" ? n.similarity + 1 : n.similarity) * this._w[n.index] + 1e-9;
49
+ votes[this._y[n.index]] += w;
50
+ }
51
+ const sum = votes.reduce((a, b) => a + b, 0);
52
+ return sum > 0 ? votes.map((v) => v / sum) : votes.map(() => 1 / this.classes);
53
+ }
54
+ predict(x) {
55
+ const scores = this.proba(x);
56
+ return { scores, confidence: topProbability(scores) };
57
+ }
58
+ }
59
+ /** Index `samples` for kNN classification. */
60
+ export function fitKnn(samples, opts = {}) {
61
+ featureDim(samples.map((s) => s.x));
62
+ const classes = opts.classes ?? classCount(samples.map((s) => s.y));
63
+ const model = new KnnModel(Math.min(opts.k ?? 5, samples.length), opts.metric ?? "cosine", classes);
64
+ for (const s of samples)
65
+ model.add(s.x, s.y, s.weight ?? 1);
66
+ return model;
67
+ }
68
+ //# sourceMappingURL=knn.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"knn.js","sourceRoot":"","sources":["../../../src/ml/classical/knn.ts"],"names":[],"mappings":"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"}