Skip to main content

ResidualCodec

Struct ResidualCodec 

Source
pub struct ResidualCodec {
    pub nbits: usize,
    pub centroids: CentroidStore,
    pub avg_residual: Array1<f32>,
    pub bucket_cutoffs: Option<Array1<f32>>,
    pub bucket_weights: Option<Array1<f32>>,
    pub byte_reversed_bits_map: Vec<u8>,
    pub bucket_weight_indices_lookup: Option<Array2<usize>>,
}
Expand description

A codec that manages quantization parameters and lookup tables for the index.

This struct contains all tensors required to compress embeddings during indexing and decompress vectors during search. It uses pre-computed lookup tables to accelerate bit unpacking operations.

Fields§

§nbits: usize

Number of bits used to represent each residual bucket (e.g., 2 or 4)

§centroids: CentroidStore

Coarse centroids (codebook) of shape [num_centroids, dim]. Can be either owned (in-memory) or memory-mapped for reduced RAM usage.

§avg_residual: Array1<f32>

Average residual vector, used to reduce reconstruction error

§bucket_cutoffs: Option<Array1<f32>>

Boundaries defining which bucket a residual value falls into

§bucket_weights: Option<Array1<f32>>

Values (weights) corresponding to each quantization bucket

§byte_reversed_bits_map: Vec<u8>

Lookup table (256 entries) for byte-to-bits unpacking

§bucket_weight_indices_lookup: Option<Array2<usize>>

Maps byte values directly to bucket indices for fast decompression

Implementations§

Source§

impl ResidualCodec

Source

pub fn new( nbits: usize, centroids: Array2<f32>, avg_residual: Array1<f32>, bucket_cutoffs: Option<Array1<f32>>, bucket_weights: Option<Array1<f32>>, ) -> Result<Self>

Creates a new ResidualCodec and pre-computes lookup tables.

§Arguments
  • nbits - Number of bits per code (e.g., 2 bits = 4 buckets)
  • centroids - Coarse centroids of shape [num_centroids, dim]
  • avg_residual - Global average residual
  • bucket_cutoffs - Quantization boundaries (optional, for indexing)
  • bucket_weights - Reconstruction values (optional, for search)
Source

pub fn new_with_store( nbits: usize, centroids: CentroidStore, avg_residual: Array1<f32>, bucket_cutoffs: Option<Array1<f32>>, bucket_weights: Option<Array1<f32>>, ) -> Result<Self>

Creates a new ResidualCodec with a specified centroid storage backend.

This is the internal constructor that supports both owned and mmap centroids.

Source

pub fn embedding_dim(&self) -> usize

Returns the embedding dimension

Source

pub fn num_centroids(&self) -> usize

Returns the number of centroids

Source

pub fn centroids_view(&self) -> ArrayView2<'_, f32>

Returns a view of the centroids.

This is zero-copy for both owned and mmap centroids.

Source

pub fn compress_into_codes(&self, embeddings: &Array2<f32>) -> Array1<usize>

Compress embeddings into centroid codes using nearest neighbor search.

Uses batch matrix multiplication for efficiency: scores = embeddings @ centroids.T -> [N, K] codes = argmax(scores, axis=1) -> [N]

When the cuda feature is enabled and a GPU is available, this function automatically uses CUDA acceleration. No code changes required.

§Arguments
  • embeddings - Embeddings of shape [N, dim]
§Returns

Centroid indices of shape [N]

Source

pub fn compress_into_codes_cpu(&self, embeddings: &Array2<f32>) -> Array1<usize>

CPU implementation of compress_into_codes. This is useful when you want to explicitly avoid CUDA overhead for small batches.

Source

pub fn quantize_residuals(&self, residuals: &Array2<f32>) -> Result<Array2<u8>>

Quantize residuals into packed bytes.

Uses vectorized bucket search and parallel processing for efficiency.

§Arguments
  • residuals - Residual vectors of shape [N, dim]
§Returns

Packed residuals of shape [N, dim * nbits / 8] as bytes

Source

pub fn decompress( &self, packed_residuals: &Array2<u8>, codes: &ArrayView1<'_, usize>, ) -> Result<Array2<f32>>

Decompress residuals from packed bytes using lookup tables.

§Arguments
  • packed_residuals - Packed residuals of shape [N, packed_dim]
  • codes - Centroid codes of shape [N]
§Returns

Reconstructed embeddings of shape [N, dim]

Source

pub fn load_from_dir(index_path: &Path) -> Result<Self>

Load codec from index directory

Source

pub fn load_mmap_from_dir(index_path: &Path) -> Result<Self>

Load codec from index directory with memory-mapped centroids.

This is similar to load_from_dir but uses memory-mapped I/O for the centroids file, reducing RAM usage. The other small tensors (bucket weights, etc.) are still loaded into memory as they are negligible in size.

Use this when loading for MmapIndex to minimize memory footprint.

Trait Implementations§

Source§

impl Clone for ResidualCodec

Source§

fn clone(&self) -> ResidualCodec

Returns a duplicate of the value. Read more
1.0.0 · Source§

fn clone_from(&mut self, source: &Self)

Performs copy-assignment from source. Read more

Auto Trait Implementations§

Blanket Implementations§

Source§

impl<T> Any for T
where T: 'static + ?Sized,

Source§

fn type_id(&self) -> TypeId

Gets the TypeId of self. Read more
Source§

impl<T> Borrow<T> for T
where T: ?Sized,

Source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
Source§

impl<T> BorrowMut<T> for T
where T: ?Sized,

Source§

fn borrow_mut(&mut self) -> &mut T

Mutably borrows from an owned value. Read more
Source§

impl<T> CloneToUninit for T
where T: Clone,

Source§

unsafe fn clone_to_uninit(&self, dest: *mut u8)

🔬This is a nightly-only experimental API. (clone_to_uninit)
Performs copy-assignment from self to dest. Read more
Source§

impl<T> From<T> for T

Source§

fn from(t: T) -> T

Returns the argument unchanged.

Source§

impl<T, U> Into<U> for T
where U: From<T>,

Source§

fn into(self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

Source§

impl<T> IntoEither for T

Source§

fn into_either(self, into_left: bool) -> Either<Self, Self>

Converts self into a Left variant of Either<Self, Self> if into_left is true. Converts self into a Right variant of Either<Self, Self> otherwise. Read more
Source§

fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
where F: FnOnce(&Self) -> bool,

Converts self into a Left variant of Either<Self, Self> if into_left(&self) returns true. Converts self into a Right variant of Either<Self, Self> otherwise. Read more
Source§

impl<T> Pointable for T

Source§

const ALIGN: usize

The alignment of pointer.
Source§

type Init = T

The type for initializers.
Source§

unsafe fn init(init: <T as Pointable>::Init) -> usize

Initializes a with the given initializer. Read more
Source§

unsafe fn deref<'a>(ptr: usize) -> &'a T

Dereferences the given pointer. Read more
Source§

unsafe fn deref_mut<'a>(ptr: usize) -> &'a mut T

Mutably dereferences the given pointer. Read more
Source§

unsafe fn drop(ptr: usize)

Drops the object pointed to by the given pointer. Read more
Source§

impl<T> ToOwned for T
where T: Clone,

Source§

type Owned = T

The resulting type after obtaining ownership.
Source§

fn to_owned(&self) -> T

Creates owned data from borrowed data, usually by cloning. Read more
Source§

fn clone_into(&self, target: &mut T)

Uses borrowed data to replace owned data, usually by cloning. Read more
Source§

impl<T, U> TryFrom<U> for T
where U: Into<T>,

Source§

type Error = Infallible

The type returned in the event of a conversion error.
Source§

fn try_from(value: U) -> Result<T, <T as TryFrom<U>>::Error>

Performs the conversion.
Source§

impl<T, U> TryInto<U> for T
where U: TryFrom<T>,

Source§

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.
Source§

fn try_into(self) -> Result<U, <U as TryFrom<T>>::Error>

Performs the conversion.
Source§

impl<V, T> VZip<V> for T
where V: MultiLane<T>,

Source§

fn vzip(self) -> V