Skip to main content

Crate kanonak_expression

Crate kanonak_expression 

Source
Expand description

Kanonak expression runtime (expressionRuntimeVersion “1”).

A small, deterministic tree-walker that folds a kanonak.org/transformations (tx) + kanonak.org/math expression tree to a single number. A faithful port of the reference TypeScript kernel, verified against the shared parity vectors — including the determinism traps (Round half-away-from-zero, floored Modulo, Sign(0)=0, comparisons as 1/0).

Three layers, exactly as the reference establishes:

  1. DISPATCH — operator_arity derives an operator’s operand shape from its tx superclass: UnaryNumericOp -> unary value; BinaryArithmetic / BinaryComparison -> binary; BooleanLogic -> n-ary operands; plus the two structural shapes the hierarchy can’t imply (Not’s operand, Clip’s ternary).
  2. PRIMITIVES — the authored, determinism-bearing folds (unary / binary).
  3. THE FOLD — evaluate: operators recurse + apply a primitive; literals yield their numeric value; EVERYTHING ELSE (a typed VarRef, a domain Step/Time/Smooth, any future leaf) is handed to the caller’s resolve. The runtime never privileges tx.VarRef — it is just one leaf a domain may resolve.

Value domain: uniform f64. Booleans and comparison results are 1.0/0.0.

Operator/literal type tags are matched against &'static str literals (the frozen canonical URIs) — no allocation in the evaluation hot path, which matters for the per-step integrators (e.g. RK4) that re-evaluate an equation thousands of times.

Structs§

EvalOptions
Optional evaluation context for the ordered comparisons (IsAtLeast, Dominates). Absent (or missing a needed entry), an ordered comparison fails loudly — never a silent false from a missing table.
ExpressionError
An evaluation error. Determinism traps (Divide/Modulo by zero, Ln/Log10 of <=0, Sqrt of <0) and structural problems raise this — never NaN/Inf.
TraceNode
One node of an evaluation trace — the verdict tree explain returns. Mirrors the expression: typ is the node’s type URI, value its result (1.0/0.0 for booleans), children the operand traces in evaluation order. A short-circuited operand is simply ABSENT from children — the trace is truthful about what ran. Ordered comparisons carry their resolved operand identities as left_ref/right_ref instead of children. This is a runtime return shape, not an ontology class.

Constants§

EXPRESSION_RUNTIME_VERSION
The frozen expression-runtime version (determinism contract). Not hashed.

Functions§

evaluate
Evaluate an expression tree to a number. Operators fold via the frozen dispatch + primitive tables; literals yield their numeric value; any other node is delegated to resolve.
evaluate_with_options
evaluate with the ordered-comparison evaluation context (closures + identity-leaf resolution). options is only consulted when an IsAtLeast / Dominates node is reached; None is valid for trees without them.
explain
Evaluate an expression tree and return the verdict tree — the regex-debugger view: every evaluated node, its own result, and (for ordered comparisons) the identities it compared. The root’s value is exactly what evaluate returns for the same inputs; the conformance suite runs every vector through both and requires agreement, so the two entry points cannot drift. Kept separate from evaluate so the hot path never pays for trace allocation. Errors propagate exactly as in evaluate — a failed evaluation yields an error, not a partial trace.

Type Aliases§

ClosureTable
The transitive closures ordered comparisons consult, keyed by the ordering property’s canonical URI, then by member: closures[property][from] is the set of members from reaches. Flat, already-closed data — typically the SDK reasoner’s prp-trp saturation emitted at code-generation time. The kernel does set membership only; it never computes a closure, resolves a package, or reasons.
Resolve
Resolve any node the kernel does not recognise as an operator or literal — a binding (tx.VarRef, a domain’s typed refersTo VarRef) or a domain leaf (Step, Time, Smooth…) — to a number. ctx is opaque caller state. recurse is handed back so a domain leaf containing sub-expressions can recurse into the kernel.
ResolveRef
Resolve an identity leaf inside an ordered comparison — any operand node that is not a tx.UriLiteral — to a member’s canonical versionless URI (publisher/package/name). The identity-domain mirror of Resolve: the kernel owns the constant leaf, the caller owns bindings.