@hviana/sema 0.3.0 → 0.4.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.
- package/AGENTS.md +71 -5
- package/CONTRIBUTING.md +92 -10
- package/LICENSE.md +2 -2
- package/dist/src/derive/src/deduction.d.ts +12 -1
- package/dist/src/derive/src/deduction.js +5 -1
- package/dist/src/derive/src/index.d.ts +1 -0
- package/dist/src/geometry.d.ts +3 -30
- package/dist/src/geometry.js +330 -82
- package/dist/src/index.d.ts +1 -0
- package/dist/src/index.js +1 -0
- package/dist/src/meter.d.ts +171 -0
- package/dist/src/meter.js +269 -0
- package/dist/src/mind/attention.d.ts +0 -4
- package/dist/src/mind/attention.js +251 -23
- package/dist/src/mind/bridge.d.ts +10 -1
- package/dist/src/mind/bridge.js +179 -10
- package/dist/src/mind/canonical.d.ts +6 -1
- package/dist/src/mind/canonical.js +6 -1
- package/dist/src/mind/graph-search.d.ts +9 -0
- package/dist/src/mind/graph-search.js +59 -19
- package/dist/src/mind/junction.d.ts +10 -0
- package/dist/src/mind/junction.js +14 -0
- package/dist/src/mind/match.d.ts +40 -0
- package/dist/src/mind/match.js +125 -1
- package/dist/src/mind/mechanisms/cast.js +63 -6
- package/dist/src/mind/mechanisms/extraction.d.ts +0 -34
- package/dist/src/mind/mechanisms/extraction.js +1 -88
- package/dist/src/mind/mechanisms/recall.d.ts +3 -0
- package/dist/src/mind/mechanisms/recall.js +77 -14
- package/dist/src/mind/mind.d.ts +55 -4
- package/dist/src/mind/mind.js +110 -91
- package/dist/src/mind/pipeline-mechanism.d.ts +33 -3
- package/dist/src/mind/pipeline-mechanism.js +179 -10
- package/dist/src/mind/pipeline.js +52 -10
- package/dist/src/mind/primitives.d.ts +11 -15
- package/dist/src/mind/primitives.js +47 -28
- package/dist/src/mind/reasoning.d.ts +7 -1
- package/dist/src/mind/reasoning.js +40 -8
- package/dist/src/mind/recognition.js +93 -20
- package/dist/src/mind/traverse.d.ts +11 -0
- package/dist/src/mind/traverse.js +58 -5
- package/dist/src/mind/types.d.ts +28 -5
- package/dist/src/store.d.ts +15 -0
- package/dist/src/store.js +91 -6
- package/package.json +1 -1
- package/src/derive/src/deduction.ts +15 -0
- package/src/derive/src/index.ts +1 -0
- package/src/geometry.ts +350 -122
- package/src/index.ts +1 -0
- package/src/meter.ts +333 -0
- package/src/mind/attention.ts +268 -31
- package/src/mind/bridge.ts +187 -10
- package/src/mind/canonical.ts +6 -1
- package/src/mind/graph-search.ts +60 -21
- package/src/mind/junction.ts +12 -0
- package/src/mind/match.ts +146 -1
- package/src/mind/mechanisms/cast.ts +62 -6
- package/src/mind/mechanisms/extraction.ts +2 -103
- package/src/mind/mechanisms/recall.ts +84 -17
- package/src/mind/mind.ts +139 -98
- package/src/mind/pipeline-mechanism.ts +203 -13
- package/src/mind/pipeline.ts +65 -8
- package/src/mind/primitives.ts +49 -33
- package/src/mind/reasoning.ts +39 -7
- package/src/mind/recognition.ts +89 -19
- package/src/mind/traverse.ts +59 -5
- package/src/mind/types.ts +28 -5
- package/src/store.ts +75 -6
- package/test/14-scaling.test.mjs +17 -7
- package/test/31-audit.test.mjs +4 -1
- package/test/33-multi-candidate.test.mjs +13 -1
- package/test/36-already-answered-fusion.test.mjs +10 -3
- package/test/46-recognise-multibyte-edge.test.mjs +3 -3
- package/test/53-cross-region-probe-instrumentation.test.mjs +36 -6
- package/test/55-cost-meter.test.mjs +284 -0
- package/test/56-bridge-identity-admission.test.mjs +209 -0
- package/test/57-fusion-order.test.mjs +104 -0
- package/test/58-subquantum-sites.test.mjs +112 -0
- package/test/59-fold-invariance.test.mjs +226 -0
package/AGENTS.md
CHANGED
|
@@ -145,6 +145,14 @@ matcher or projection, add it **to the shared family** with a derived gate
|
|
|
145
145
|
aligning, edge-following to a fixpoint, predecessor-picking, or fan-out capping
|
|
146
146
|
is reintroducing duplication that was deliberately removed.
|
|
147
147
|
|
|
148
|
+
A shared analysis must not live inside a mechanism. If `pipeline-mechanism.ts`
|
|
149
|
+
(the shared contract and `Precomputed`) or a post-grounding stage has to import
|
|
150
|
+
_out of_ `mechanisms/`, the dependency is inverted and the market's decoupling
|
|
151
|
+
(2.6) is broken — deleting that mechanism would break the shared container. The
|
|
152
|
+
span-shape family (`isSpanShaped` / `containsSpan` / `skillExemplar`) was
|
|
153
|
+
exactly this and now lives in `match.ts`, where its two consumers can reach it
|
|
154
|
+
without knowing extraction exists.
|
|
155
|
+
|
|
148
156
|
Related single-definition contracts (define once, import everywhere):
|
|
149
157
|
|
|
150
158
|
- `canonical.ts` — the write/read contract for canonical segmentation
|
|
@@ -327,7 +335,49 @@ _Follow it:_ when your code can degrade, emit a counter or trace step. And mind
|
|
|
327
335
|
the classic trap: **empty bytes are truthy** — `Uint8Array(0)` passes
|
|
328
336
|
`if (answer)`; always test `.length`.
|
|
329
337
|
|
|
330
|
-
### 2.14
|
|
338
|
+
### 2.14 Measured, not guessed — the work meter
|
|
339
|
+
|
|
340
|
+
`src/meter.ts` is the one computational-usage accounting surface: a `Meter`
|
|
341
|
+
counts the WORK one inference call performs at every layer (store reads by kind
|
|
342
|
+
and by VOLUME, ANN queries and vectors scanned, perceptions, recognitions,
|
|
343
|
+
climbs and ancestor visits, alignment cells, chart pops, mechanism floors/runs)
|
|
344
|
+
and times named PHASES. Off by default and free when off;
|
|
345
|
+
`new Mind({ profile:
|
|
346
|
+
true })` attaches one per response and leaves a
|
|
347
|
+
`CostReport` on `mind.lastCost`. `bench/profile-inference.mjs` is the reference
|
|
348
|
+
harness.
|
|
349
|
+
|
|
350
|
+
It is the profiling counterpart of the rationale — the rationale says why an
|
|
351
|
+
answer was chosen, the meter says what it cost. Four contracts:
|
|
352
|
+
|
|
353
|
+
1. **Never read by inference.** A counter that reached a decision would end
|
|
354
|
+
determinism (2.1). Write-only from the engine's side.
|
|
355
|
+
2. **Counts are the product; times are the hint.** Counters are deterministic,
|
|
356
|
+
so two runs are diffable and a work regression is visible without a
|
|
357
|
+
stopwatch. Only `elapsedMs` and the phase millisecond totals are not.
|
|
358
|
+
3. **Phases nest, and carry their own counter deltas.** `think` ⊃ `<mech>.run` ⊃
|
|
359
|
+
`substitutionBridge` ⊃ `recall.exhaustiveResonate`. Inclusive, never summed —
|
|
360
|
+
but each phase reports the work done inside it (`PhaseCost.counters`), which
|
|
361
|
+
is what makes "which phase did those byte reads?" answerable at all.
|
|
362
|
+
4. **Count a logical operation once.** A recursive read (`bytesPrefix`
|
|
363
|
+
descending a branch) is charged at the public entry point only — the private
|
|
364
|
+
`_prefix` body is uncharged. Counting the recursion made one read of an
|
|
365
|
+
N-byte branch report as N reads, so the counter measured tree size instead of
|
|
366
|
+
read requests.
|
|
367
|
+
5. **Shared analyses are charged to themselves.** `attention`, `weave`,
|
|
368
|
+
`spanShaped` and `substitutionBridge` bill their own phase, not the mechanism
|
|
369
|
+
that happened to first-touch them — otherwise the profile blames whoever paid
|
|
370
|
+
on everyone's behalf (it once read "cast.floor costs 2.9 s" when 2.7 s of
|
|
371
|
+
that was the consensus climb).
|
|
372
|
+
|
|
373
|
+
_Follow it:_ a new layer that wants to be visible bumps a field in `meter.ts` —
|
|
374
|
+
never a private counter. (`danglingReads`/`compactFailures` in `store.ts` stay:
|
|
375
|
+
those are session-lifetime HEALTH counters, not per-response work.) Add the
|
|
376
|
+
counter to the report the same way, and remember the classic trap: **profile
|
|
377
|
+
without a trace attached** — a trace bypasses the memos (2.11) and measures a
|
|
378
|
+
different machine.
|
|
379
|
+
|
|
380
|
+
### 2.15 Comment style
|
|
331
381
|
|
|
332
382
|
Comments state _constraints and failure modes_ — "this guard exists because X
|
|
333
383
|
breaks without it", often naming the test that pins the behaviour — never
|
|
@@ -360,6 +410,7 @@ story of the fix.
|
|
|
360
410
|
| Learning / ingestion / training cache | `src/mind/learning.ts`, `src/ingest-cache.ts` |
|
|
361
411
|
| Post-grounding (reason, fuse, articulate) | `src/mind/reasoning.ts`, `src/mind/articulation.ts` |
|
|
362
412
|
| Rationale / trace | `src/mind/rationale.ts`, `src/mind/trace.ts` |
|
|
413
|
+
| Computational-usage meter | `src/meter.ts` (harness: `bench/profile-inference.mjs`) |
|
|
363
414
|
| Extension host types | `src/extension.ts` |
|
|
364
415
|
| Sublibraries (own READMEs, own tests) | `src/derive/`, `src/alu/`, `src/rabitq-ivf/` |
|
|
365
416
|
|
|
@@ -427,6 +478,19 @@ recognition found, how the climb voted, which edges were followed
|
|
|
427
478
|
(`disambiguate` steps carry the evidence). `recall-echo` means "nearest stored
|
|
428
479
|
form, not a derived fact". Remember traced responses bypass memos (2.11).
|
|
429
480
|
|
|
481
|
+
### Profile an answer
|
|
482
|
+
|
|
483
|
+
```ts
|
|
484
|
+
const mind = new Mind({ store, profile: true }); // no trace — see 2.14
|
|
485
|
+
await mind.respondText(query);
|
|
486
|
+
console.log(formatReport(mind.lastCost!)); // counters by layer + nested phases
|
|
487
|
+
```
|
|
488
|
+
|
|
489
|
+
`bench/profile-inference.mjs` runs a battery this way and prints per-query and
|
|
490
|
+
aggregate reports; `sumReports` aggregates a run. Diff the COUNTERS between two
|
|
491
|
+
runs to catch a work regression — they are deterministic; read the PHASES to see
|
|
492
|
+
where the wall clock went.
|
|
493
|
+
|
|
430
494
|
### Train at scale
|
|
431
495
|
|
|
432
496
|
Use `CachedIngest` (`ingest-cache.ts`) as a drop-in for `mind.ingest` — it
|
|
@@ -450,10 +514,12 @@ against the built `dist/` (`npm test`; one suite:
|
|
|
450
514
|
- New behaviour ⇒ a test in the matching numbered suite, or a new numbered
|
|
451
515
|
suite.
|
|
452
516
|
- Many tests pin **contracts that look like implementation details** (the bridge
|
|
453
|
-
tier order,
|
|
454
|
-
|
|
455
|
-
|
|
456
|
-
|
|
517
|
+
tier order, the bridge's identity admission vs. its prefix trap and the
|
|
518
|
+
scaffolding reading behind it, the two span-shape readings (`match.ts`),
|
|
519
|
+
`MechanismResult.complete`, determinism, honest silence). A "simplification"
|
|
520
|
+
that fails an existing test is wrong until you can argue the _test_ is wrong —
|
|
521
|
+
several guards exist precisely because a plausible simplification once failed
|
|
522
|
+
a dozen suites.
|
|
457
523
|
- Sublibraries test themselves (`src/{alu,derive,rabitq-ivf}/test/`) with zero
|
|
458
524
|
Sema dependency. Keep it so.
|
|
459
525
|
- Performance claims are tested (the rabitq-ivf benchmark asserts sub-linear
|
package/CONTRIBUTING.md
CHANGED
|
@@ -1,15 +1,97 @@
|
|
|
1
|
-
# Contributing
|
|
1
|
+
# Contributing to Sema
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
Thank you for your interest in contributing to Sema.
|
|
4
4
|
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
1.0.0;
|
|
9
|
-
- this project is source-available, not formally open source;
|
|
10
|
-
- commercial use requires a separate paid license;
|
|
11
|
-
- you will not submit secrets, credentials, private keys, or confidential data.
|
|
5
|
+
Sema is source-available software distributed publicly under the PolyForm
|
|
6
|
+
Noncommercial License 1.0.0. Commercial use requires a separate commercial
|
|
7
|
+
license from the Sema licensor.
|
|
12
8
|
|
|
13
|
-
|
|
9
|
+
## Contributor representations
|
|
14
10
|
|
|
11
|
+
By submitting a contribution to Sema, you represent that:
|
|
12
|
+
|
|
13
|
+
- you created the contribution or otherwise have the legal right to submit it
|
|
14
|
+
under these terms;
|
|
15
|
+
- the contribution does not knowingly violate any copyright, patent, trade
|
|
16
|
+
secret, contractual obligation, or other third-party right;
|
|
17
|
+
- you have obtained any authorization required from your employer or another
|
|
18
|
+
rights holder;
|
|
19
|
+
- you have clearly identified any third-party material included in the
|
|
20
|
+
contribution and provided its applicable license and copyright notices;
|
|
21
|
+
- the contribution does not contain secrets, credentials, private keys,
|
|
22
|
+
confidential information, or unlawfully obtained material;
|
|
23
|
+
- if the contribution was created with the assistance of an artificial
|
|
24
|
+
intelligence system, you have reviewed it and remain responsible for its
|
|
25
|
+
origin, legality, correctness, and compliance with these terms.
|
|
26
|
+
|
|
27
|
+
## Contribution license grant
|
|
28
|
+
|
|
29
|
+
You retain ownership of the copyright in your contribution.
|
|
30
|
+
|
|
31
|
+
By intentionally submitting a contribution for inclusion in Sema, you grant
|
|
32
|
+
Henrique Viana, as the author, copyright holder, and licensor of Sema, and his
|
|
33
|
+
successors and assigns, a worldwide, perpetual, irrevocable, non-exclusive,
|
|
34
|
+
royalty-free, transferable, and sublicensable license to:
|
|
35
|
+
|
|
36
|
+
- use, reproduce, modify, adapt, and prepare derivative works from the
|
|
37
|
+
contribution;
|
|
38
|
+
- combine the contribution with Sema or other materials;
|
|
39
|
+
- publicly display, publicly perform, distribute, make available, host, and
|
|
40
|
+
otherwise exploit the contribution;
|
|
41
|
+
- offer, license, and sublicense the contribution as part of Sema under the
|
|
42
|
+
PolyForm Noncommercial License 1.0.0;
|
|
43
|
+
- offer, license, and sublicense the contribution as part of commercial,
|
|
44
|
+
proprietary, source-available, or other versions of Sema;
|
|
45
|
+
- relicense the contribution as part of Sema under current or future licensing
|
|
46
|
+
terms.
|
|
47
|
+
|
|
48
|
+
This license grant does not transfer ownership of your contribution to Henrique
|
|
49
|
+
Viana. You remain free to use and license your original contribution
|
|
50
|
+
independently, provided that doing so does not violate rights belonging to Sema
|
|
51
|
+
or to third parties.
|
|
52
|
+
|
|
53
|
+
## Patent license
|
|
54
|
+
|
|
55
|
+
To the extent that you own or control patent claims necessarily infringed by
|
|
56
|
+
your contribution, you grant Henrique Viana, his successors and assigns, and
|
|
57
|
+
recipients of Sema a worldwide, perpetual, irrevocable, non-exclusive,
|
|
58
|
+
royalty-free, transferable, and sublicensable patent license to make, use, sell,
|
|
59
|
+
offer for sale, import, and otherwise exploit your contribution as part of Sema.
|
|
60
|
+
|
|
61
|
+
This patent license terminates for any party that initiates patent litigation
|
|
62
|
+
alleging that Sema or a contribution incorporated into Sema infringes a patent.
|
|
63
|
+
|
|
64
|
+
## No obligation to accept contributions
|
|
65
|
+
|
|
66
|
+
Submitting a contribution does not guarantee that it will be accepted, merged,
|
|
67
|
+
published, maintained, or included in any public or commercial version of Sema.
|
|
68
|
+
|
|
69
|
+
The project maintainer may modify, reject, remove, or replace an accepted
|
|
70
|
+
contribution.
|
|
71
|
+
|
|
72
|
+
## Developer Certificate of Origin
|
|
73
|
+
|
|
74
|
+
All commits must include a Developer Certificate of Origin sign-off:
|
|
75
|
+
|
|
76
|
+
```bash
|
|
15
77
|
git commit -s
|
|
78
|
+
```
|
|
79
|
+
|
|
80
|
+
The sign-off must use your real name and an email address you are authorized to
|
|
81
|
+
use:
|
|
82
|
+
|
|
83
|
+
```text
|
|
84
|
+
Signed-off-by: Your Name <your.email@example.com>
|
|
85
|
+
```
|
|
86
|
+
|
|
87
|
+
The sign-off certifies the origin and authorization of each commit. It does not
|
|
88
|
+
replace the contribution license grant described in this document.
|
|
89
|
+
|
|
90
|
+
## Acceptance
|
|
91
|
+
|
|
92
|
+
By opening or submitting a pull request, patch, or other contribution intended
|
|
93
|
+
for inclusion in Sema, you confirm that you have read and agree to these
|
|
94
|
+
contribution terms.
|
|
95
|
+
|
|
96
|
+
Contributions submitted on behalf of a company or another organization must be
|
|
97
|
+
authorized by the applicable rights holder.
|
package/LICENSE.md
CHANGED
|
@@ -2,8 +2,8 @@
|
|
|
2
2
|
|
|
3
3
|
<https://polyformproject.org/licenses/noncommercial/1.0.0>
|
|
4
4
|
|
|
5
|
-
> Required Notice: Copyright
|
|
6
|
-
> Reis
|
|
5
|
+
> Required Notice: Copyright © Henrique Viana (author). Marcelo Oliveira dos
|
|
6
|
+
> Reis and Rogerio Nascimento (supporters).
|
|
7
7
|
|
|
8
8
|
## Acceptance
|
|
9
9
|
|
|
@@ -118,8 +118,19 @@ export interface Derivation<I> {
|
|
|
118
118
|
/** Derivations of the rule's premises (empty for an axiom). */
|
|
119
119
|
premises: Array<Derivation<I>>;
|
|
120
120
|
}
|
|
121
|
+
/** Optional search-effort read-out, filled in place while the search runs.
|
|
122
|
+
* A plain structural record so the sublibrary stays firewalled (it imports
|
|
123
|
+
* nothing from Sema, and Sema copies these into its own accounting). Purely
|
|
124
|
+
* observational: the search never reads it back. */
|
|
125
|
+
export interface SearchStats {
|
|
126
|
+
/** Agenda entries popped, stale lazy-deletion entries included — the chart
|
|
127
|
+
* work actually done. */
|
|
128
|
+
pops: number;
|
|
129
|
+
/** Agenda entries pushed by a successful relaxation. */
|
|
130
|
+
pushes: number;
|
|
131
|
+
}
|
|
121
132
|
/**
|
|
122
133
|
* Find a lightest derivation of a goal item, or `null` if none exists.
|
|
123
134
|
* `cost` on the returned root is the total derivation cost.
|
|
124
135
|
*/
|
|
125
|
-
export declare function lightestDerivation<I>(system: DeductionSystem<I
|
|
136
|
+
export declare function lightestDerivation<I>(system: DeductionSystem<I>, stats?: SearchStats): Derivation<I> | null;
|
|
@@ -43,7 +43,7 @@ import { MinHeap } from "./priority-queue.js";
|
|
|
43
43
|
* Find a lightest derivation of a goal item, or `null` if none exists.
|
|
44
44
|
* `cost` on the returned root is the total derivation cost.
|
|
45
45
|
*/
|
|
46
|
-
export function lightestDerivation(system) {
|
|
46
|
+
export function lightestDerivation(system, stats) {
|
|
47
47
|
const g = new Map(); // best known cost per item
|
|
48
48
|
const proof = new Map(); // producing rule per item
|
|
49
49
|
const items = new Map(); // key → the item it stands for
|
|
@@ -82,6 +82,8 @@ export function lightestDerivation(system) {
|
|
|
82
82
|
g.set(key, cost);
|
|
83
83
|
proof.set(key, rule);
|
|
84
84
|
items.set(key, item);
|
|
85
|
+
if (stats)
|
|
86
|
+
stats.pushes++;
|
|
85
87
|
agenda.push(cost + h(item, key), { key, g: cost });
|
|
86
88
|
}
|
|
87
89
|
};
|
|
@@ -89,6 +91,8 @@ export function lightestDerivation(system) {
|
|
|
89
91
|
relax(item, cost, null);
|
|
90
92
|
while (agenda.size > 0) {
|
|
91
93
|
const { value } = agenda.pop();
|
|
94
|
+
if (stats)
|
|
95
|
+
stats.pops++;
|
|
92
96
|
const key = value.key;
|
|
93
97
|
// Lazy deletion: an entry is stale if a cheaper derivation has since been
|
|
94
98
|
// recorded for the same item.
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
export { lightestDerivation } from "./deduction.js";
|
|
2
|
+
export type { SearchStats } from "./deduction.js";
|
|
2
3
|
export type { DeductionSystem, Derivation, PooledConclusion, PooledContribution, Rule, } from "./deduction.js";
|
|
3
4
|
export { coverSequence } from "./rewrite.js";
|
|
4
5
|
export type { CandidateSpan, Cover } from "./rewrite.js";
|
package/dist/src/geometry.d.ts
CHANGED
|
@@ -105,6 +105,7 @@ export interface Grid {
|
|
|
105
105
|
data: Uint8Array;
|
|
106
106
|
dims?: number[];
|
|
107
107
|
}
|
|
108
|
+
export declare function contentBoundaries(space: Space, bytes: Uint8Array): number[];
|
|
108
109
|
/** Find the longest prefix of `bytes` whose leaf-id signature matches a
|
|
109
110
|
* known branch via `lookup`. Returns the byte-length of that prefix, or 0. */
|
|
110
111
|
export declare function knownPrefixLength(bytes: Uint8Array, leafAt: (i: number) => number | null, lookup: (leafIds: number[]) => number | null): number;
|
|
@@ -129,9 +130,8 @@ export declare function bytesToTree(space: Space, alphabet: Alphabet, bytes: Uin
|
|
|
129
130
|
* grown stream whose boundary set EXTENDS a previous fold's reuses every
|
|
130
131
|
* matching segment's Folded unchanged (segments fold independently by
|
|
131
132
|
* construction, so reuse is bit-identical to refolding) and folds only the
|
|
132
|
-
* new right-edge segment — O(turn) per extension
|
|
133
|
-
*
|
|
134
|
-
* never depends on cache state. */
|
|
133
|
+
* new right-edge segment — O(turn) per extension. Purely a cache: the
|
|
134
|
+
* produced tree never depends on cache state. */
|
|
135
135
|
export interface StableFold {
|
|
136
136
|
edges: number[];
|
|
137
137
|
segs: Folded[];
|
|
@@ -170,33 +170,6 @@ export interface StructuralPart {
|
|
|
170
170
|
* concatenated byte string, and never interns or stores a new node: the
|
|
171
171
|
* result is an opaque, ungrounded Vec for an ANN probe only. */
|
|
172
172
|
export declare function composeStructuralGist(space: Space, parts: readonly StructuralPart[]): Vec;
|
|
173
|
-
/** The PLAIN fold's full level pyramid — every level's item list, bottom
|
|
174
|
-
* (leaves) to top (root). Left-grouped folding is RADIX-ALIGNED: the item
|
|
175
|
-
* at level L, index i, covers exactly bytes [i·mg^L, (i+1)·mg^L) whenever
|
|
176
|
-
* it is a FULL block, and a full block folds bit-identically in ANY byte
|
|
177
|
-
* string that contains it at that offset. So a string extended by a
|
|
178
|
-
* suffix (a conversation's accumulated context) reuses every full block of
|
|
179
|
-
* its prefix's pyramid and refolds only the right edge of each level —
|
|
180
|
-
* O(suffix + depth·mg) per extension instead of O(whole), with the
|
|
181
|
-
* produced tree BIT-IDENTICAL to a from-scratch plain fold (same nodes,
|
|
182
|
-
* same FP ops; reused subtrees are shared objects, and Sema nodes are
|
|
183
|
-
* never mutated). Purely an implementation cache: structure and numerics
|
|
184
|
-
* never depend on whether a pyramid was available. */
|
|
185
|
-
export interface FoldPyramid {
|
|
186
|
-
levels: Array<Array<{
|
|
187
|
-
tree: Sema;
|
|
188
|
-
len: number;
|
|
189
|
-
}>>;
|
|
190
|
-
bytes: number;
|
|
191
|
-
}
|
|
192
|
-
/** Plain bytes→tree (identical to capability-less {@link bytesToTree}) that
|
|
193
|
-
* also RETURNS its pyramid, reusing `prev` — the pyramid of a PROPER
|
|
194
|
-
* prefix of `bytes` (caller guarantees content match and
|
|
195
|
-
* prev.bytes < bytes.length). */
|
|
196
|
-
export declare function bytesToTreePyramid(space: Space, alphabet: Alphabet, bytes: Uint8Array, prev?: FoldPyramid): {
|
|
197
|
-
tree: Sema;
|
|
198
|
-
pyramid: FoldPyramid;
|
|
199
|
-
};
|
|
200
173
|
export declare function hilbertBytes(grid: Grid): Uint8Array;
|
|
201
174
|
export declare function gridToTree(space: Space, alphabet: Alphabet, grid: Grid): Sema;
|
|
202
175
|
export declare function stackGrids(frames: Grid[]): Grid;
|