Azure AI 搜索支持标量和二进制量化,以减少搜索索引中矢量的大小。 建议使用量化,因为它可减少 float16 和 float32 嵌入的内存和磁盘存储。 要抵消有损压缩的影响,可以添加过度采样和重新评分。
若要使用内置量化,请执行以下步骤:
- 从矢量字段和对索引的
vectorSearch
配置开始 - 添加
vectorSearch.compressions
- 添加
scalarQuantization
或binaryQuantization
配置,并为其命名 - 设置可选属性以缓解有损索引的影响
- 创建使用命名配置的新矢量配置文件
- 创建具有新向量特性的新向量场
- 使用您定义的配置,在索引编制期间将量化的 float32 或 float16 数据加载到索引中。
- (可选)使用过度采样参数 查询量化数据 。 如果矢量字段在其定义中未指定过度采样,则可以在查询时添加它。
-
搜索索引中的矢量字段,其中
vectorSearch
配置指定分层可导航小世界 (HNSW) 或详尽的 k-最近的邻域 (eKNN) 算法以及新的矢量配置文件。
量化适用于接收浮点类型向量的向量场。 在本文的示例中,对于传入 float32 嵌入项,字段的数据类型为 Collection(Edm.Single)
,但是也支持 float16。 在配置了压缩的字段中接收向量时,引擎会执行量化以减少内存中和磁盘上的向量数据的占用空间。
支持两种类型的量化:
标量量化将浮点值压缩为更窄的数据类型。 AI 搜索目前支持 int8,即 8 位,减少了向量索引大小四倍。
二进制量化将浮点转换为二进制位,其占用 1 位。 这会导致矢量索引大小减少多达 28 倍。
备注
虽然免费服务支持量化,但由于存储配额有限,它们不会演示完整的存储节省。
重新记录是一种用于抵消因矢量压缩而丢失信息的技术。 它使用过度采样来选取额外的向量,并补充信息来重新评分查询找到的初始结果。 补充信息要么是未压缩的原始全精度矢量,要么仅用于二进制量化,可以选择使用二进制量化文档候选项针对查询向量重新评分。 索引中指定了重新记录选项,但如果索引支持,则可以在查询时调用重新记录。
API 版本确定哪种重新评分行为适用于你的代码。 最新的预览 API 支持用于二进制量化的新重新评分方法。 使用 2025-03-01-preview
创建的索引可以使用新的重新评分行为。
API 版本 | 量化类型 | 重新评分属性 |
---|---|---|
2024-07-01 | 标量和二进制量化,使用分层可导航小世界 (HNSW) 图构建的向量索引进行相似性搜索 | rerankWithOriginalVectors |
2024-11-01-预览版 | HNSW 图形上的标量和二进制量化 |
rescoringOptions.enableRescoring 和 rescoreStorageMethod.preserveOriginals |
2025-03-01-预览版 | HNSW 图形上的二进制量化 | 仍支持以前的参数组合,但如果删除原始嵌入,现在可以重新记录二进制量化: rescoringOptions.enableRescoring rescoringOptions.rescoreStorageMethod=discardOriginals |
仅 HNSW 图形允许重新评分。 详尽的 k-最近的邻域 (eKNN) 不支持重新评分。
重新评分的通用过程为:
- 矢量查询通过压缩的矢量字段执行。
- 矢量查询返回前 K 个过度采样候选项。
- 使用未压缩的原始向量或二进制量化的点积对过度采样的 k 个候选项进行重新评分。 1. 重新评分后,将调整结果,以便首先显示更相关的匹配项。
如何在索引中指定vectorsSearch.compressions
部分将在本节中进行说明。 以下示例显示了包含向量字段的字段集合的分部索引定义。
压缩示例包括两者 scalarQuantization
或 binaryQuantization
。 可以根据需要指定任意数量的压缩配置,然后将所需配置分配给矢量配置文件。
vectorSearch.Compressions
稳定 REST API 和预览版 REST API 之间的语法有所不同,预览版添加了更多用于存储优化的选项,以及对现有语法的更改。 后向兼容性通过内部 API 映射保留,但我们建议在面向 2024-11-01-preview 和将来版本的代码中采用较新的属性。
使用创建索引或创建或更新索引 REST API 配置压缩设置。
POST https://[servicename].search.azure.cn/indexes?api-version=2024-07-01
{
"name": "my-index",
"fields": [
{ "name": "Id", "type": "Edm.String", "key": true, "retrievable": true, "searchable": true, "filterable": true },
{ "name": "content", "type": "Edm.String", "retrievable": true, "searchable": true },
{ "name": "vectorContent", "type": "Collection(Edm.Single)", "retrievable": false, "searchable": true, "dimensions": 1536,"vectorSearchProfile": "vector-profile-1"},
],
"vectorSearch": {
"profiles": [
{
"name": "vector-profile-1",
"algorithm": "use-hnsw",
"compression": "use-scalar"
}
],
"algorithms": [
{
"name": "use-hnsw",
"kind": "hnsw",
"hnswParameters": { },
"exhaustiveKnnParameters": null
}
],
"compressions": [
{
"name": "use-scalar",
"kind": "scalarQuantization",
"scalarQuantizationParameters": {
"quantizedDataType": "int8"
},
"rerankWithOriginalVectors": true,
"defaultOversampling": 10
},
{
"name": "use-binary",
"kind": "binaryQuantization",
"rerankWithOriginalVectors": true,
"defaultOversampling": 10
}
]
}
}
要点:
kind
必须设置为scalarQuantization
或binaryQuantization
。rerankWithOriginalVectors
使用原始的未压缩矢量来重新计算相似性,并对初始搜索查询返回的最匹配的结果重新排名。 即使stored
为 false,未压缩的向量也存在于搜索索引中。 此属性是可选的。 默认值为 true。defaultOversampling
将考虑更广泛的潜在结果,以抵消量化导致的信息减少。 潜在结果的公式由查询中的k
和过采样乘数组成。 例如,如果查询指定k
为 5,并且过采样为 20,则查询实际上会请求 100 个文档用于重新排序,并为此使用原始未压缩向量。 只返回重新排序后的前k
个结果。 此属性是可选的。 默认值为 4。quantizedDataType
是可选的,仅适用于标量量化。 如果添加它,则必须将其设置为int8
。 这是目前唯一支持标量量化的基元数据类型。 默认值为int8
。
可以在 2024-11-01-preview REST API 或更高版本中使用 HNSW 算法或穷举 KNN。 对于稳定版,请仅使用 HNSW。 如果要重新评分,则必须选择 HNSW。
"vectorSearch": {
"profiles": [ ],
"algorithms": [
{
"name": "use-hnsw",
"kind": "hnsw",
"hnswParameters": {
"m": 4,
"efConstruction": 400,
"efSearch": 500,
"metric": "cosine"
}
}
],
"compressions": [ <see previous section>]
}
若要使用新的量化配置,必须创建新的矢量配置文件。 要在内存中构建压缩索引,需要创建新的矢量配置文件。 新的配置文件使用 HNSW。
在同一索引定义中,创建新的矢量配置文件,并添加压缩属性和算法。 下面是两个配置文件,每个量化方法使用其中一个。
"vectorSearch": { "profiles": [ { "name": "vector-profile-hnsw-scalar", "compression": "use-scalar", "algorithm": "use-hnsw", "vectorizer": null }, { "name": "vector-profile-hnsw-binary", "compression": "use-binary", "algorithm": "use-hnsw", "vectorizer": null } ], "algorithms": [ <see previous section> ], "compressions": [ <see previous section> ] }
将矢量配置文件分配给新矢量字段。 字段的数据类型为 float32 或 float16。
在 Azure AI 搜索中,float32 和 float16 类型的实体数据模型 (EDM) 等效项分别
Collection(Edm.Single)
和Collection(Edm.Half)
。{ "name": "vectorContent", "type": "Collection(Edm.Single)", "searchable": true, "retrievable": true, "dimensions": 1536, "vectorSearchProfile": "vector-profile-hnsw-scalar", }
使用用于拉取模型索引的索引器或用于推送模型索引的 API 加载索引。
标量量化降低了每个向量嵌入中每个数字的分辨率。 它没有将每个数字描述为 16 位或 32 位浮点数,而是使用 8 位整数。 它标识一系列数字(通常是第 99 个百分位数的最小值和最大值),将它们划分为有限数量的级别或容器,并为每个容器分配一个标识符。 在 8 位标量量化中,有 2^8 或 256 个可能的 bin。
向量的每个分量都被映射到这组量化级别内最接近的代表值,其过程类似于将实数舍入到最接近的整数。 在量化的 8 位向量中,标识符号代替原始值。 量化后,每个向量都由其分量所属的 bin 的标识符数组表示。 与原始向量相比,这些量化向量需要存储的位数要少得多,从而减少所需存储和内存占用。
二进制量化通过将每个组件表示为一个位(0 或 1)来压缩高维向量。 此方法可大幅减少内存占用,并加速矢量比较操作,这对于搜索和检索任务至关重要。 基准测试表明矢量索引的大小最多可减少 96%。
这对于维度大于 1024 的嵌入尤其有效。 对于较小的维度,我们建议测试二进制量化的质量,或改为尝试标量。 此外,我们发现在嵌入以零为中心时,二进制量化效果非常出色。 最常见的嵌入模型,如 OpenAI、Cohere 和 Mistral 都是以零为中心的。
压缩或量化向量字段的查询语法与非压缩矢量字段的语法相同,除非你想要重写与过度采样和重新记录关联的参数。 可以添加 oversampling
参数,以在查询时调用过度采样和重新记录。
回想一下,索引中的矢量压缩定义具有 rerankWithOriginalVectors
和 defaultOversampling
,用于缓解有损压缩的影响。 可以重写默认值,以在查询时改变行为。 例如,如果 defaultOversampling
为 10.0,可以在查询请求中将其更改为其他值。
即使索引没有显式 rerankWithOriginalVectors
或 defaultOversampling
定义,也可以设置过采样参数。 在查询时提供 oversampling
会替代该查询的索引设置,并执行有效 rerankWithOriginalVectors
为 true 的查询。
POST https://[service-name].search.azure.cn/indexes/demo-index/docs/search?api-version=2024-07-01
{
"vectorQueries": [
{
"kind": "vector",
"vector": [8, 2, 3, 4, 3, 5, 2, 1],
"fields": "myvector",
"oversampling": 12.0,
"k": 5
}
]
}
要点:
适用于根据向量配置文件分配进行矢量压缩的向量字段。
在查询时替代
defaultOversampling
值或引入过度采样,即使索引的压缩配置未指定过度采样或重新排序选项也是如此。