【RAG】【vector_stores053】Milvus全文搜索向量存储示例分析
案例目标
本案例展示了如何使用LlamaIndex和Milvus向量数据库构建支持全文搜索和混合搜索的检索增强生成(RAG)系统。通过Milvus 2.5的Sparse-BM25方法,原始文本可以自动转换为稀疏向量,无需手动生成稀疏嵌入,从而实现混合搜索策略,平衡语义理解与关键词相关性。
案例从实现纯全文搜索开始,然后通过集成语义搜索增强功能,提供更全面的搜索结果。这种混合搜索方法在单一方法不足的情况下特别有用,可以显著提高信息检索的准确性和相关性。
技术栈与核心依赖
LlamaIndex Milvus OpenAI BM25算法 全文搜索 混合搜索
# 核心依赖包 pip install llama-index-vector-stores-milvus pip install llama-index-embeddings-openai pip install llama-index-llms-openai本示例使用了OpenAI的嵌入模型和GPT模型,但也可以使用其他嵌入模型和LLM。Milvus 2.5的Sparse-BM25方法支持自动将原始文本转换为稀疏向量,无需手动生成稀疏嵌入。
环境配置
运行此示例需要以下环境配置:
- 安装必要的Python包:llama-index-vector-stores-milvus、llama-index-embeddings-openai和llama-index-llms-openai
- 设置OpenAI API密钥
- 配置Milvus服务器URI(可以是本地服务器或Zilliz Cloud)
- 下载示例数据(Paul Graham的文章)
# OpenAI API配置 import openai openai.api_key = "sk-" # Milvus配置 URI = "http://localhost:19530" # 本地Milvus服务器 # TOKEN = "" # 如果使用Zilliz Cloud,需要设置TOKEN注意:全文搜索目前支持Milvus Standalone、Milvus Distributed和Zilliz Cloud,但尚不支持Milvus Lite(计划在未来实现)。如果需要更多信息,可以联系support@zilliz.com。
案例实现
本案例的实现分为两个主要部分:全文搜索实现和混合搜索实现。
1. 导入必要的库和模块
from llama_index.core import SimpleDirectoryReader, VectorStoreIndex, StorageContext from llama_index.vector_stores.milvus import MilvusVectorStore from llama_index.vector_stores.milvus.utils import BM25BuiltInFunction from llama_index.core import Settings2. 加载文档
# 使用SimpleDirectoryReader加载文档 documents = SimpleDirectoryReader("./data/paul_graham/").load_data()3. 实现全文搜索
首先,我们实现仅使用全文搜索的RAG系统:
# 跳过密集嵌入模型 Settings.embed_model = None # 构建Milvus向量存储,仅启用稀疏向量 vector_store = MilvusVectorStore( uri=URI, enable_dense=False, # 禁用密集向量 enable_sparse=True, # 启用稀疏向量,用于全文搜索 sparse_embedding_function=BM25BuiltInFunction(), overwrite=True, ) # 存储文档到Milvus storage_context = StorageContext.from_defaults(vector_store=vector_store) index = VectorStoreIndex.from_documents( documents, storage_context=storage_context )上述代码将示例文档插入Milvus并构建索引,以启用BM25排名进行全文搜索。它禁用了密集嵌入,并使用默认参数的BM25BuiltInFunction。
4. 执行全文搜索查询
import textwrap # 创建查询引擎,使用稀疏向量模式 query_engine = index.as_query_engine( vector_store_query_mode="sparse", similarity_top_k=5 ) answer = query_engine.query("What did the author learn at Viaweb?") print(textwrap.fill(str(answer), 100))5. 自定义文本分析器
分析器在全文搜索中起着至关重要的作用,通过将句子分解为标记并执行词法处理,如词干提取和停用词移除。它们通常是特定于语言的。Milvus支持两种类型的分析器:内置分析器和自定义分析器。
bm25_function = BM25BuiltInFunction( analyzer_params={ "tokenizer": "standard", "filter": [ "lowercase", # 内置过滤器 {"type": "length", "max": 40}, # 自定义单个标记的大小上限 {"type": "stop", "stop_words": ["of", "to"]}, # 自定义停用词 ], }, enable_match=True, )6. 实现混合搜索
混合搜索系统结合了语义搜索和全文搜索,优化了RAG系统中的检索性能。以下示例使用OpenAI嵌入进行语义搜索,使用BM25进行全文搜索:
# 创建向量存储,同时启用密集向量和稀疏向量 vector_store = MilvusVectorStore( uri=URI, dim=1536, # OpenAI嵌入的维度 enable_sparse=True, # 启用稀疏向量 sparse_embedding_function=BM25BuiltInFunction(), overwrite=True, # hybrid_ranker="RRFRanker", # hybrid_ranker默认为"RRFRanker" # hybrid_ranker_params={}, # hybrid_ranker_params默认为{} ) storage_context = StorageContext.from_defaults(vector_store=vector_store) index = VectorStoreIndex.from_documents( documents, storage_context=storage_context, embed_model="default", # "default"将使用OpenAI嵌入 )这种方法将文档存储在具有两个向量字段的Milvus集合中:
embedding:由OpenAI嵌入模型生成的密集嵌入,用于语义搜索sparse_embedding:使用BM25BuiltInFunction计算的稀疏嵌入,用于全文搜索
此外,我们应用了使用"RRFRanker"及其默认参数的重新排名策略。要自定义重新排名器,可以按照Milvus重新排名指南配置hybrid_ranker和hybrid_ranker_params。
7. 执行混合搜索查询
# 创建混合搜索查询引擎 query_engine = index.as_query_engine( vector_store_query_mode="hybrid", similarity_top_k=5 ) answer = query_engine.query("What did the author learn at Viaweb?") print(textwrap.fill(str(answer), 100))这种混合方法通过利用语义和基于关键字的检索,确保在RAG系统中提供更准确、上下文感知的响应。
案例效果
本案例成功实现了以下功能:
1. 全文搜索实现
成功实现了基于BM25算法的全文搜索功能,能够根据关键词精确匹配文档内容,并按照相关性对结果进行排名。通过禁用密集嵌入并启用稀疏嵌入,系统专注于文本的关键词匹配,提供了精确的搜索结果。
2. 混合搜索实现
成功实现了结合语义搜索和全文搜索的混合搜索功能,通过同时使用密集向量和稀疏向量,系统能够同时理解语义含义和匹配关键词,提供更全面和准确的搜索结果。
3. 自定义文本分析器
展示了如何自定义文本分析器,通过配置分词器、过滤器等参数,优化全文搜索的效果,提高搜索的准确性和相关性。
4. 搜索效果对比
通过对比全文搜索和混合搜索的结果,可以看出混合搜索在保持关键词匹配准确性的同时,能够更好地理解查询的语义含义,提供更全面和相关的搜索结果。
| 搜索方式 | 优点 | 缺点 |
|---|---|---|
| 全文搜索 | 精确匹配关键词,结果可预测 | 无法理解语义含义,可能错过相关内容 |
| 语义搜索 | 理解语义含义,能找到相关内容 | 可能错过精确关键词匹配 |
| 混合搜索 | 结合两者优点,提供更全面准确的结果 | 实现复杂度较高 |
案例实现思路
本案例的实现思路如下:
- 全文搜索原理:全文搜索使用精确的关键词匹配,通常利用BM25等算法对文档进行相关性排名。在RAG系统中,这种方法检索相关文本以增强AI生成的响应。
- Milvus Sparse-BM25方法:利用Milvus 2.5的Sparse-BM25方法,原始文本可以自动转换为稀疏向量,无需手动生成稀疏嵌入,简化了全文搜索的实现。
- 向量存储配置:创建MilvusVectorStore对象,配置Milvus服务器的连接参数、集合名称、向量维度等。通过设置enable_dense和enable_sparse参数控制是否启用密集向量和稀疏向量。
- BM25BuiltInFunction:使用BM25BuiltInFunction作为稀疏嵌入函数,自动应用BM25算法对文本进行分词和评分,实现全文搜索功能。
- 混合搜索策略:通过同时启用密集向量和稀疏向量,并使用RRFRanker进行重新排名,实现混合搜索策略,平衡语义理解和关键词相关性。
- 文本分析器定制:通过配置analyzer_params参数,自定义文本分析器,包括分词器、过滤器等,优化全文搜索的效果。
整个实现充分利用了Milvus 2.5的新特性,特别是Sparse-BM25方法和混合搜索功能,通过结合语义搜索和全文搜索,提供了更全面和准确的搜索结果。案例中的代码实现清晰展示了如何配置和使用这些功能,为开发者构建高效的RAG系统提供了参考。
扩展建议
基于本案例,可以考虑以下扩展方向:
- 高级重新排名策略:探索更复杂的重新排名策略,如使用机器学习模型对搜索结果进行重新排序,提高搜索结果的准确性。
- 多语言支持:扩展对多语言的支持,为不同语言配置适当的文本分析器和停用词列表,提高多语言搜索的准确性。
- 动态权重调整:根据查询类型和内容动态调整语义搜索和全文搜索的权重,优化不同场景下的搜索效果。
- 查询意图识别:添加查询意图识别功能,根据用户意图自动选择最适合的搜索模式(全文搜索、语义搜索或混合搜索)。
- 搜索结果可视化:开发搜索结果可视化工具,直观展示不同搜索模式的结果差异和重叠部分,帮助用户理解搜索结果。
- 性能优化:针对大规模数据集进行性能优化,如使用分片、索引优化等技术,提高搜索速度和系统吞吐量。
- 实时更新:实现文档的实时更新和增量索引,确保搜索结果始终反映最新的文档内容。
- 用户反馈循环:添加用户反馈机制,收集用户对搜索结果的评价,利用这些反馈不断优化搜索算法和参数。
总结
本案例详细展示了如何使用LlamaIndex和Milvus 2.5构建支持全文搜索和混合搜索的RAG系统。通过利用Milvus的Sparse-BM25方法,实现了自动将原始文本转换为稀疏向量的功能,简化了全文搜索的实现。
案例的核心价值在于:
- 展示了全文搜索和混合搜索在RAG系统中的应用和优势
- 提供了具体的代码实现,演示了如何配置和使用Milvus的全文搜索功能
- 展示了如何自定义文本分析器,优化全文搜索的效果
- 提供了可复用的代码实现,便于开发者应用到实际项目中
通过进一步的扩展和优化,可以构建出更加高效和智能的搜索系统,满足各种复杂搜索需求。全文搜索和混合搜索技术将成为构建高效RAG系统的重要手段,值得开发者深入研究和应用。
