/* tslint:disable */ /* eslint-disable */ export class CompressedIndex { private constructor(); free(): void; [Symbol.dispose](): void; /** * Add a single vector to the index (streaming/incremental). * * Algorithm 1 steps: * 1. Extract norm from the embedding * 2. Normalize: x_hat = x / ||x|| * 3. Rotate: y = Pi * x_hat * 4. Quantize each coordinate * 5. Pack indices and append to storage */ add_vector(quantizer: TurboQuantizer, embedding: Float32Array): void; /** * Add multiple vectors to the index in batch (appends to existing data). * * `embeddings_flat`: n × dim float32 values, row-major. * `n`: number of vectors to add. */ add_vectors(quantizer: TurboQuantizer, embeddings_flat: Float32Array, n: number): void; /** * Deserialize an index from a binary blob produced by `save()`. */ static load(data: Uint8Array): CompressedIndex; /** * Create an empty index ready to receive vectors incrementally. * * - `dim`: embedding dimension (must match the TurboQuantizer) * - `bits`: bits per coordinate (1–8, must match the TurboQuantizer) */ static new_empty(dim: number, bits: number): CompressedIndex; /** * Serialize the index to a compact binary blob (for IndexedDB / localStorage). * * Format: [dim:u32][bits:u8][n_vectors:u32][row_bytes:u32] + packed + norms(f32 LE) */ save(): Uint8Array; /** * Search for top-k by approximate inner product. * * KEY OPTIMIZATION: We compute scores in the ROTATED domain. * Since Π is orthogonal, ⟨x, q⟩ = ⟨Πx, Πq⟩. * * Steps: * 1. Rotate query once: q_rot = Π · q — O(d²), done once * 2. For each database vector i: — O(d) per vector * score_i = ‖x_i‖ · Σ_j c_{idx_{i,j}} · q_rot_j * * This avoids the O(d²) inverse rotation per database vector. */ search(quantizer: TurboQuantizer, query: Float32Array, k: number): Uint32Array; readonly memory_bytes: number; readonly n_vectors: number; } export class TurboQuantizer { free(): void; [Symbol.dispose](): void; /** * Decode: look up centroids, apply Π^T, scale by norm. * * DEQUANT_mse (Algorithm 1, lines 9–11): * ỹ_j = c_{idx_j} * x̃ = Π^T · ỹ (then multiply by norm) */ decode(indices: Uint8Array, norm: number): Float32Array; /** * Encode a single vector. Returns (indices, norm). * * Algorithm 1 steps: * 1. ‖x‖ → stored as norm * 2. x̂ = x / ‖x‖ * 3. y = Π · x̂ (each y_j ∈ [-1, 1]) * 4. idx_j = argmin_k |y_j − c_k| */ encode(embedding: Float32Array): Uint8Array; /** * Extract the norm of an embedding vector. */ encode_norm(embedding: Float32Array): number; /** * Estimate inner product between a compressed vector and a full-precision query. * * Uses the rotated-domain optimization: * score = norm * Σ_j centroid[idx_j] * (Π·q)_j */ inner_product_estimate(indices: Uint8Array, norm: number, query: Float32Array): number; /** * Create a new TurboQuantizer for the TurboQuant MSE variant (Algorithm 1). * * - `dim`: embedding dimension (e.g. 384, 768, 1536) * - `bits`: bits per coordinate (1–4, extendable to 8) * - `seed`: random seed for the rotation matrix Π (deterministic) */ constructor(dim: number, bits: number, seed: bigint); readonly bits: number; readonly compression_ratio: number; readonly dim: number; /** * Get the expected MSE for unit vectors (Theorem 1). */ readonly expected_mse: number; } /** * Build a compressed index from a flat array of embeddings. * * `embeddings_flat`: n_vectors × dim float32 values, row-major. * `n_vectors`: number of vectors. */ export function build_index(quantizer: TurboQuantizer, embeddings_flat: Float32Array, n_vectors: number): CompressedIndex;