跳到主要内容

稀疏-密集(sparse-dense)嵌入

Pinecone支持稀疏和密集值的向量,这使得您能够在一个查询中对数据执行语义和关键字搜索,并将结果组合以获得更相关的结果。本主题描述了Pinecone中稀疏-密集(sparse-dense)向量的工作原理。

要了解稀疏-密集(sparse-dense)嵌入的实际应用,请参见电子商务混合搜索示例

Pinecone稀疏-密集(sparse-dense)向量允许关键字感知语义搜索

Pinecone稀疏-密集(sparse-dense)向量允许您执行关键词感知的语义搜索。对于跨领域查询的语义搜索结果可能不太相关;将这些结果与关键词搜索结果结合起来可以提高相关性

由于Pinecone允许您创建自己的稀疏向量,因此您可以使用稀疏-密集(sparse-dense)查询来解决任何实值稀疏-密集(sparse-dense)向量的最大内积搜索(MIPS)问题。这包括使用SPLADE检索文本数据学习稀疏表示的新兴用例。

稀疏-密工作流程

使用稀疏-密集(sparse-dense)向量涉及以下一般步骤:

  • 使用外部嵌入模型创建密集向量。

  • 使用外部模型创建稀疏向量。

  1. Create an index that supports sparse-dense vectors (s1 or p1 with the dotproduct metric).
  • 向索引中插入密集向量和稀疏向量。

  • 使用稀疏-密集(sparse-dense)向量搜索索引。

  • Pinecone 返回稀疏-密集(sparse-dense)向量。

Pinecone 中的稀疏和密集向量

Pinecone 支持将稠密向量和稀疏向量作为单个向量嵌入。这些类型的嵌入表示不同类型的信息,并启用不同类型的搜索。稠密向量启用语义搜索。语义搜索根据特定的距离度量返回最相似的结果,即使没有精确匹配也可以。这是可能的,因为由嵌入模型生成的稠密向量,例如SBERT,是语义含义的数值表示。

稀疏向量具有非常大的维度,其中只有一小部分值是非零的。当用于关键字搜索时,每个稀疏向量表示一个文档;维度表示字典中的单词,值表示这些单词在文档中的重要性。关键字搜索算法(如BM25算法)根据关键字匹配的数量、频率和其他因素计算文本文档的相关性。

创建稀疏向量嵌入

关键字感知的语义搜索需要文档的向量表示。由于Pinecone索引接受稀疏索引而不是文档,因此可以控制生成稀疏向量以表示文档。

有关稀疏向量生成的示例,请参见 解释稀疏向量搜索的SPLADE,我们的 SPLADE生成笔记本,以及我们的 BM25生成笔记本

ℹ️注意

Pinecone支持最多1000个非零值的稀疏向量值。

Pinecone从您的稀疏和密集嵌入中创建稀疏密集向量

在Pinecone中,每个向量都由密集向量值和可选的稀疏向量值组成。 Pinecone不支持仅具有稀疏值的向量。

p1和s1索引使用“点积”(dotproduct)距离度量支持稀疏-密集(sparse-dense)向量

Pinecone将稀疏-密集(sparse-dense)向量存储在p1和s1索引中。要使用稀疏值查询索引,该索引必须使用dotproduct度量。尝试使用其他任何索引查询稀疏值都会返回错误。

2023年2月22日之前创建的索引不支持稀疏值。

稀疏-密集(sparse-dense)查询包括稀疏和密集向量值

要查询您的稀疏-密集(sparse-dense)向量,您需要提供一个包含稀疏和密集值的查询向量。 Pinecone通过考虑整个向量上的完整点积来对您的索引向量进行排名;向量的得分是其密集值与查询的密集部分的点积和其稀疏值与查询的稀疏部分的点积之和。

稀疏-密集(sparse-dense)向量格式

Pinecone将稀疏值表示为两个数组的字典:indicesvalues。您可以将这些值upsert到一个向量参数中,以 upsert一个稀疏-密集(sparse-dense)向量

示例

以下示例插入了两个具有稀疏和密集值的向量。

Python

index = pinecone.Index('example-index') 

upsert_response = index.upsert(
vectors=[
{'id': 'vec1',
'values': [0.1, 0.2, 0.3],
'metadata': {'genre': 'drama'},
'sparse_values': {
'indices': [10, 45, 16],
'values': [0.5, 0.5, 0.2]
}},
{'id': 'vec2',
'values': [0.2, 0.3, 0.4],
'metadata': {'genre': 'action'},
'sparse_values': {
'indices': [15, 40, 11],
'values': [0.4, 0.5, 0.2]
}}
],
namespace='example-namespace'
)

以下示例使用稀疏-密集(sparse-dense)向量查询索引。

Python

query_response = index.query(
namespace="example-namespace",
top_k=10,
vector=[0.1, 0.2, 0.3],
sparse_vector={
'indices': [10, 45, 16],
'values': [0.5, 0.5, 0.2]
}
)

稀疏-密集(sparse-dense)查询不支持显式加权

因为Pinecone的索引将您的稀疏密集向量视为单个向量,它不提供用于调整查询的密集部分与其稀疏部分权重的内置参数;索引对向量中的坐标的密度或稀疏性是不可知的。然而,您可以通过自定义查询向量来将线性加权方案纳入其中,如下面的函数所示。

示例

以下示例使用alpha参数转换向量值。

Python

def hybrid_score_norm(dense, sparse, alpha: float):
"""Hybrid score using a convex combination

alpha * dense + (1 - alpha) * sparse

Args:
dense: Array of floats representing
sparse: a dict of `indices` and `values`
alpha: scale between 0 and 1
"""
if alpha < 0 or alpha > 1:
raise ValueError("Alpha must be between 0 and 1")
hs = {
'indices': sparse['indices'],
'values': [v * (1 - alpha) for v in sparse['values']]
}
return [v * alpha for v in dense], hs

以下示例使用上述函数转换向量,然后查询Pinecone索引。

Python

sparse_vector = {
'indices': [10, 45, 16],
'values': [0.5, 0.5, 0.2]
}
dense_vector = [0.1, 0.2, 0.3]

hdense, hsparse = hybrid_score_norm(dense_vector, sparse_vector, alpha=0.75)

query_response = index.query(
namespace="example-namespace",
top_k=10,
vector=hdense,
sparse_vector=hsparse
)

下一步