在这篇文章中,我们将介绍多语言向量搜索。我们将使用 Microsoft E5 多语言嵌入模型,该模型在零样本和多语言设置中具有最先进的性能。我们将介绍多语言嵌入的一般工作原理,以及如何在 Elasticsearch 中使用 E5。
近年来,向量搜索席卷了搜索和信息检索领域。它能够将查询的语义与文档相匹配,合并文本的上下文和含义,并为用户提供前所未有的自然语言查询能力。向量搜索是促进大型语言模型 (LLM) 的重要上下文来源,它为生成式 AI 时代越来越多的现代搜索体验提供动力。
当研究人员第一次开始使用和训练向量搜索的嵌入模型时,他们使用了他们能找到的最广泛可用的数据集。然而,这些数据集往往都是英语。查询是英文的,维基百科索引的文章也是英文的。所以非英语世界很快就注意到了这个问题,针对中文、中文、法语、日语等语言的特定语言的语言模型慢慢开始出现。然而,这些模型只能在该语言中使用。但借助嵌入的强大功能,我们最终还是找到了办法,训练出了使用单个模型就可将多种语言嵌入到同一“嵌入空间”中的模型。你可以将嵌入空间视为与语言无关的。
既然我们可以将文本、图像和音频嵌入到嵌入空间中,为什么不将多种语言嵌入到同一个嵌入空间中呢?这就是多语言嵌入模型背后的想法。通过对齐的训练数据集(包含不同语言的相似句子的数据集),可以使模型学习的不是语言之间的单词翻译,而是每个句子背后的关系和含义,而与语言无关。这是一个真正的跨语言模型,能够处理其所训练的任何语言的文本对。现在让我们看看如何使用这些对齐的多语言模型。
在本练习中,当英语和中文的句子具有相同的基本含义时,我们会将它们映射到嵌入空间的同一部分。假设我们有以下句子,我想对其进行索引和搜索。
在下面的示例查询中,我们展示了多语言嵌入如何克服传统词汇检索在多语言搜索中面临的一些挑战。通常我们谈论向量搜索克服了词法搜索的语义不匹配和词汇不匹配的限制。语义不匹配是指我们在查询中使用的标记(单词)与索引文档中的形式相同,但含义不同的情况。例如,"苹果的iphone"与"美味的苹果"中的“苹果”含义不同。由于词汇不匹配,我们面临着标记不同,但潜在的概念或含义与文档中表示的含义相似。我们可能会搜索“ATM”,它没有出现在任何文档中,但与“保存钱币的银行”密切相关。除了词法搜索的这两项改进之外,多语言(跨语言)嵌入还增加了语言独立性,允许使用不同的语言进行查询和传递。
现在让我们尝试一些搜索示例,看看它是如何工作的。
查询:“riverside”(中文:“河边”)
召回结果:
在此示例中,我们搜索的词汇 “riverside” 在中文中的翻译为“河边”。然而,该单词的语义与英语短语“bank of the River”以及中文关键字“河岸”匹配,因此,这两个文档被召回
查询:“自动取款机”(英语:“ATM”)
召回结果:
在此示例中,“自动取款机”的英文翻译为“ATM”。“自动取款机”和“ATM”都没有作为关键字出现在任何文档中,但语义含义接近英语短语“bank … Money”和中文短语“银行...钱”。在这种情况下,上下文很重要,查询指的是持有货币的银行,而不是河岸(bank of the river),因此我们仅召回引用此类“银行”的文档,但我们这样做基于语义而不是关键字的跨语言。
查询:“运动”
召回结果:
在此示例中,我们正在搜索文本中表示的运动类型。我们对运动或行走感兴趣,而不是坐在一处或一动不动。因此,最接近的文档由中文单词“去了”和英语单词“walked”表示。
查询:“静止”
召回结果:
如果我们反转示例 3a 中的查询并查找“静止”或缺乏运动,我们会得到“相反”的结果。
2022 年 12 月,微软发布了一种名为 E5 的新通用嵌入模型,即EmbEddings from bidirEctionalEncoder rEpresentations。(我知道,命名事物很困难。)该模型在一个名为 CCPairs 的特殊的纯英文数据集上进行训练,并在训练过程中引入了一些新方法。该模型很快就在众多基准测试中名列前茅,在该模型成功后,他们将目光投向了非英语领域。除了嵌入英语模型之外,微软后来还使用各种多语言数据集在多语言文本上训练了 E5 模型的变体,但总体过程与英语模型相同。这表明他们的训练过程在很大程度上帮助产生了如此好的英语嵌入,并且这种成功也转移到了多语言嵌入上。在一些纯英语基准测试中,多语言嵌入甚至比仅在英语数据集上训练的其他嵌入更好!有兴趣的可以看看MTEB 检索基准了解更多详细信息。
正如嵌入模型的常见做法,E5 系列提供三种尺寸,允许用户根据其特定用例和预算在有效性和效率之间做出权衡决策。
下面我们可以看到三个多语言 E5 模型及其特征,以及在TyDi 先生的多语言基准测试上测量的有效性(看,命名很难)。作为基线和比较,我们纳入了 TyDi 先生的 BM25(词汇搜索)有效性分数,如 E5 作者报告的那样。
Effectiveness: Avg. MRR@10 | Efficiency: dimensions | Efficiency: parameters | |
---|---|---|---|
BM25 | 33.3 | n/a | n/a |
multilingual-e5-small | 64.4 | 384 | 118M |
multilingual-e5-base | 65.9 | 768 | 278M |
multilingual-e5-large | 70.5 | 1024 | 560M |
Elasticsearch 使您能够生成、存储和搜索向量嵌入。我们已经大致了解了多语言嵌入的介绍,并且对 E5 有了一些了解。让我们看一下如何将所有这些实际连接到 Elasticsearch 的搜索体验中。该博客有一个随附的 notebook,其中详细显示了上面示例中使用 Elasticsearch 端到端的所有代码。
以下是所需内容的快速概述:
现在让我们看一下笔记本中每个步骤的一些代码片段。
创建 Elastic Cloud 集群或准备另一个 Elasticsearch 集群后,我们可以使用 eland 库上传嵌入模型。
MODEL_ID = "multilingual-e5-base"
!eland_import_hub_model \
--cloud-id $CLOUD_ID \
--es-username elastic \
--es-password $ELASTIC_PASSWORD \
--hub-model-id intfloat/$MODEL_ID \
--es-model-id $MODEL_ID \
--task-type text_embedding \
--start
现在模型已上传到集群并准备好进行推理,我们可以创建包含推理处理器的摄取管道来执行我们选择的文本字段的嵌入。使用企业搜索功能(例如网络爬虫)时,您还可以通过 Kibana UI管理摄取管道。
client.ingest.put_pipeline(id="pipeline", processors=[{
"inference": {
"model_id": MODEL_ID,
"field_map": {
"passage": "text_field" # field to embed: passage
},
"target_field": "passage_embedding" # embedded field: passage_embedding
}
}])
对于上面的简单示例,我们仅使用一个非常简单的索引映射,但希望它也能让您了解您的映射可能是什么样子:
mapping = {
"properties": {
"id": { "type": "keyword" },
"language": { "type": "keyword" },
"passage": { "type": "text" },
"passage_embedding.predicted_value": {
"type": "dense_vector",
"dims": 768,
"index": "true",
"similarity": "cosine"
}
},
"_source": {
"excludes": [
"passage_embedding.predicted_value"
]
}
}
使用根据上述映射创建的索引,我们就可以提取文档了。您可以使用任何您想要的摄取方法,只要引用我们在开始时创建的摄取管道(或设置为索引的默认值)即可。请注意,与其他嵌入模型一样,E5 确实有令牌限制(512 个令牌或约 400 个单词),因此较长的文本需要在被摄取之前分块为单独的段落(例如使用 LangChain 或其他工具)。这是我们的示例文档的样子。
passages = [
{
"id": "doc1",
"language": "en",
"passage": """I sat on the bank of the river today."""
},
{
"id": "doc2",
"language": "zh",
"passage": """今天我到河岸上走走。"""
},
{
"id": "doc3",
"language": "en",
"passage": """I walked to the bank today to deposit money."""
},
{
"id": "doc4",
"language": "zh",
"passage": """我今天坐在银行等我的钱。"""
}
]
文档已被索引并创建了嵌入,因此我们准备好搜索!
client.search(index="passages", knn={
"field": "passage_embedding.predicted_value",
"query_vector_builder": {
"text_embedding": {
"model_id": MODEL_ID,
"model_text": f"query: {q}",
}
},
"k": 2, # for the demo, we're always just searching for pairs of passages
"num_candidates": 5
})
就是这样!通过上述步骤以及笔记本中的完整代码,您可以完全在 Elasticsearch 中构建自己的多语言语义搜索体验。
注意: E5 模型在嵌入之前使用文本前缀的指令进行训练。这意味着,当您想要嵌入文本进行语义搜索时,必须在查询前添加“query:”前缀,并在索引段落前添加“passage:”。有关更多详细信息和需要不同前缀的其他用例,请参阅multilingual-e5-base 模型卡中的常见问题解答。
在本博客和随附的笔记本中,我们展示了多语言向量搜索的工作原理,以及如何将 Elasticsearch 与 E5 嵌入模型结合使用。我们通过展示跨语言的多语言搜索示例来推动这一点,但实际上相同的 E5 嵌入模型也可以在单一语言中使用。例如,如果您只有一个中文文本语料库,您可以自由地使用相同的模型和相同的方法来仅使用中文查询来搜索该语料库。它们都是相同的模型,并且最终的嵌入空间相同!
另外,如果你没有办法在Elastic Cloud上部署验证, 在腾讯云Elasticsearch中也可以获得同样的体验!
原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。
如有侵权,请联系 cloudcommunity@tencent.com 删除。
原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。
如有侵权,请联系 cloudcommunity@tencent.com 删除。