Los modelos de incrustación de Voyage IA admiten dimensiones flexibles y cuantificación para ayudar a optimizar el almacenamiento y los costos de búsqueda en aplicaciones basadas en vectores. Esta página explica cómo utilizar estas funcionalidades para reducir los costos y mantener una alta calidad de recuperación.
Aprende sobre dimensiones flexibles y cuantización mediante un tutorial interactivo en Google Colab.
Overview
Cuando se trabaja con aplicaciones de búsqueda vectorial a gran escala, como recuperación de código en repositorios masivos, los costos de almacenamiento y computacionales pueden ser significativos. Estos costos se escalan linealmente con los siguientes factores:
Dimensionalidad del embedding: El número de dimensiones en cada vector
Precisión: El número de bits utilizados para codificar cada número en el vector
Al reducir uno o ambos factores, puedes disminuir considerablemente los costos sin un impacto significativo en la calidad de la recuperación. Los modelos de Voyage IA admiten dos técnicas complementarias para lograr esto:
Embeddings matryoshka: Permite usar versiones más pequeñas de los embeddings al truncarlos a menos dimensiones
Cuantización: Reduce la precisión de cada número en tus vectores de representación de 32bits de punto flotante a formatos de menor precisión
Estas técnicas se habilitan a través de Aprendizaje Matryoshka y entrenamiento consciente de la cuantización, que entrenan a los modelos para mantener la calidad incluso con dimensiones reducidas o valores cuantizados.
Incrustaciones Matryoshka
Las incrustaciones Matryoshka son un tipo especial de incrustación vectorial que contiene varias incrustaciones válidas de diferentes tamaños anidadas dentro de un solo vector. Esto le brinda la flexibilidad de elegir la dimensionalidad que mejor equilibre sus requisitos de rendimiento y costos.
Los últimos modelos de embedding de Voyage generan embeddings Matryoshka y soportan múltiples dimensiones de salida directamente a través del
output_dimension parámetro. Para obtener más información, consulte
Descripción general de los modelos.
Cómo funcionan las incrustaciones Matryoshka
Con el aprendizaje Matryoshka, una única representación contiene una familia anidada de representaciones de varias longitudes. Por ejemplo, una embedding de Voyage de 2048dimensiones contiene embeddings válidas de múltiples longitudes menores:
Las primeras 256 dimensiones forman una incrustación válida de 256dimensiones
Las primeras 512 dimensiones forman una incrustación válida de 512dimensiones
Las primeras 1024 dimensiones forman una incrustación válida de 1024dimensiones
Todas las 2048 dimensiones forman la incrustación de fidelidad total
Cada versión más corta proporciona una calidad de recuperación ligeramente inferior a la representación completa, pero requiere menos almacenamiento y recursos computacionales.
Cómo truncar incrustaciones Matryoshka
Truncar las incrustaciones de Matryoshka manteniendo el subconjunto principal de dimensiones. El siguiente ejemplo demuestra cómo truncar vectores de 1024dimensiones a 256 dimensiones:
import voyageai import numpy as np def embd_normalize(v: np.ndarray) -> np.ndarray: # Normalize rows of a 2D array to unit vectors row_norms = np.linalg.norm(v, axis=1, keepdims=True) if np.any(row_norms == 0): raise ValueError("Cannot normalize rows with a norm of zero.") return v / row_norms vo = voyageai.Client() # Generate 1024-dimensional embeddings embd = vo.embed(['Sample text 1', 'Sample text 2'], model='voyage-4-large').embeddings # Truncate to 256 dimensions and normalize short_dim = 256 resized_embd = embd_normalize(np.array(embd)[:, :short_dim]).tolist()
cuantización
La cuantificación reduce la precisión de las incrustaciones al convertir números de punto flotante de alta precisión en formatos de menor precisión. Este proceso puede reducir drásticamente los costos de almacenamiento y computación mientras se mantiene una alta calidad de recuperación.
Los modelos de embedding de Voyage más recientes se entrenan utilizando entrenamiento consciente de cuantización, lo que significa que mantienen una alta calidad de recuperación incluso cuando se cuantifican. Para obtener más información, consulte Resumen de modelos.
Nota
Muchas bases de datos que admiten el almacenamiento y la recuperación de vectores también admiten incrustaciones cuantizadas, incluida MongoDB. Para obtener más información sobre la cuantización en MongoDB Vector Search, consulte avs-quantization.
Cómo funciona la cuantización
La cuantización reduce la precisión de las incrustaciones al representar cada dimensión con menos bits que el formato de punto flotante estándar de 32bits. En lugar de usar 4 bytes por dimensión, las incrustaciones cuantificadas utilizan:
Enteros de8bits (1 byte por dimensión): Reduce el almacenamiento por 4veces
Binario (1 bit por dimensión): Reduce el almacenamiento en un 32x
A pesar de esta drástica reducción de tamaño, los modelos entrenados conscientes de la cuantización, como los de Voyage, mantienen una alta calidad de recuperación. Los modelos de Voyage compatibles permiten la cuantización especificando el tipo de datos de salida con el parámetro output_dtype:
Tipo de dato | Descripción |
|---|---|
| Cada incrustación devuelta es una lista de 324números en punto flotante de precisión simple de bits ( bytes). Esta es la por defecto y ofrece la mayor precisión y exactitud de recuperación. |
| Cada embedding devuelto es una lista de enteros de 8bits (1bytes) con un rango de -128 a 127 y de 0 a 255, respectivamente. |
| Cada embedding devuelto es una lista de enteros de 8bits que representan valores de embedding de un solo bit cuantificados y empaquetados en bits: |
Ejemplo
Comprensión de la cuantización binaria
Considera los siguientes valores de embedding:
-0.0396, 0.0062, -0.0745, -0.0390, 0.0046, 0.0003, -0.0850, 0.0399 La cuantificación binaria convierte cada valor en un solo bit, utilizando las siguientes reglas:
Los valores inferiores a
0se convierten en0Los valores mayores o iguales a
0se convierten en1
0, 1, 0, 0, 1, 1, 0, 1 Los ocho bits se integran en un entero de 8bits:
01001101. Este número entero se convierte en77en decimal.Para convertir al tipo de salida final, aplica las siguientes conversiones:
Tipo de salidaMétodo de conversiónResultadoubinaryuint8: Utiliza el valor directamente como entero sin signo.77binaryint8: Aplicar el método offset binary restando128.-51(que es igual a77 - 128)
Binario desplazado
Binario de desplazamiento es un método para representar enteros con signo en forma binaria. Voyage IA utiliza este método para el tipo de salida binary para codificar los embeddings binarios empaquetados como enteros con signo (int8).
El método binario desplazado funciona añadiendo o restando un valor de desplazamiento:
Cuando se convierte a binario: agrega
128al entero con signo antes de codificarAl convertir de binario: Reste
128del número entero después de decodificar
Para números enteros con signo de 8bits (rango -128 a 127), el desplazamiento es siempre 128.
Ejemplo
Entero con signo a binario
Para representar -32 como un número binario de 8bits:
Agrega el desplazamiento (
128) a-32, dando como resultado96.Convierte
96a binario:01100000.
Ejemplo
Binario a entero con signo
Para determinar el entero con signo a partir del número binario de 8bits 01010101:
Convierte esto directamente en un número entero:
85.Reste el desplazamiento (
128) de85, obteniendo-43.
Cómo usar la cuantización con Voyage IA
Puedes convertir manualmente las incrustaciones de coma flotante a formato binario o desempaquetar las incrustaciones binarias de vuelta a bits individuales. Los siguientes ejemplos demuestran ambas operaciones:
import numpy as np import voyageai vo = voyageai.Client() # Generate float embeddings embd_float = vo.embed('Sample text 1', model='voyage-4-large', output_dimension=2048).embeddings[0] # Compute 512-dimensional bit-packed binary and ubinary embeddings from 2048-dimensional float embeddings embd_binary_calc = (np.packbits(np.array(embd_float) > 0, axis=0) - 128).astype(np.int8).tolist() # Quantize, binary offset embd_binary_512_calc = embd_binary_calc[0:64] # Truncate. Binary is 1/8 length of embedding dimension. embd_ubinary_calc = (np.packbits(np.array(embd_float) > 0, axis=0)).astype(np.uint8).tolist() # Quantize, binary offset embd_ubinary_512_calc = embd_ubinary_calc[0:64] # Truncate. Binary is 1/8 length of embedding dimension.
import numpy as np import voyageai vo = voyageai.Client() # Generate binary embeddings embd_binary = vo.embed('Sample text 1', model='voyage-4-large', output_dtype='binary', output_dimension=2048).embeddings[0] embd_ubinary = vo.embed('Sample text 1', model='voyage-4-large', output_dtype='ubinary', output_dimension=2048).embeddings[0] # Unpack bits embd_binary_bits = [format(x, f'08b') for x in np.array(embd_binary) + 128] # List of (bits) strings embd_binary_unpacked = [bit == '1' for bit in ''.join(embd_binary_bits)] # List of booleans embd_ubinary_bits = [format(x, f'08b') for x in np.array(embd_ubinary)] # List of (bits) strings embd_ubinary_unpacked = [bit == '1' for bit in ''.join(embd_ubinary_bits)] # List of booleans