core/vocab/manifold.py
Shay bd423e489c arch: close coordinate back-door in vocab layer
- Add algebra/rotor.py: word_transition_rotor() as a free operator function
- Update algebra/__init__.py: export word_transition_rotor
- Refactor vocab/manifold.py: remove edge_rotor(), add versor grade-norm
  invariant check in add() to reject raw coordinate vectors at insertion time

VocabManifold now stores only algebraically valid Cl(4,1) versors and
exposes only relational lookup (CGA inner product). Rotor construction
is a contextual algebra-layer concern, not a vocabulary property.
2026-05-12 20:52:14 -07:00

78 lines
3 KiB
Python

"""
VocabManifold — the geometric vocabulary.
Each word is a versor in Cl(4,1). nearest(F) finds the closest word
by CGA inner product — no cosine similarity, no ANN index.
Invariant: every stored versor must satisfy the Cl(4,1) grade-norm
condition |V * reverse(V)|_scalar ≈ ±1. This is enforced at insertion
time in add(). Raw coordinate vectors (e.g. from external embeddings)
will fail this check — use normalize_to_versor() before calling add().
Rotor construction between word-versors is NOT a vocabulary concern.
Use algebra.word_transition_rotor(A, B) from the algebra layer when
a transition operator is needed in field or generation logic.
"""
import numpy as np
from algebra.cga import cga_inner
from algebra.cl41 import geometric_product, reverse
from algebra.versor import normalize_to_versor
class VocabManifold:
def __init__(self):
self._words: list = []
self._versors: list = [] # each shape (32,), grade-normed to ±1
def add(self, word: str, versor: np.ndarray) -> None:
"""
Register a word-versor pair.
Enforces the Cl(4,1) versor invariant: the scalar part of
V * reverse(V) must be ≈ ±1. This rejects any raw coordinate
vector or external embedding that has not been lifted into the
algebra. If your source is a float array from outside the system,
call normalize_to_versor() first.
Raises:
ValueError: if the grade-norm condition is not satisfied.
"""
v = np.asarray(versor, dtype=np.float32).copy()
grade_norm = float(geometric_product(v, reverse(v))[0])
if not (0.95 <= abs(grade_norm) <= 1.05):
raise ValueError(
f"Word '{word}': versor grade-norm {grade_norm:.4f} ≠ ±1. "
"Pass a valid Cl(4,1) versor. "
"If lifting from a raw array, call normalize_to_versor() first."
)
self._words.append(word)
self._versors.append(v)
def get_versor(self, word: str) -> np.ndarray:
"""Look up a word's versor. Raises KeyError if not found."""
try:
idx = self._words.index(word)
return self._versors[idx].copy()
except ValueError:
raise KeyError(f"Word '{word}' not in vocabulary.")
def nearest(self, F: np.ndarray, exclude_idx: int = -1) -> tuple:
"""
Find the word whose versor is closest to F by CGA inner product.
Returns (word, index). O(|vocab|), exact, no approximation.
cga_inner(X, Y) = -d^2 / 2 for null vectors: maximizing = minimizing distance.
"""
best_score = -np.inf
best_idx = 0
for i, v in enumerate(self._versors):
if i == exclude_idx:
continue
score = cga_inner(F, v)
if score > best_score:
best_score = score
best_idx = i
return self._words[best_idx], best_idx
def __len__(self) -> int:
return len(self._words)