向量数据库基础与最小检索示例:用 Chroma 找回相似片段
前面我们已经把文档切分成带有来源信息的片段,也知道 Embedding 可以把文本变成可比较的向量。下一步是把这些向量保存起来,并在用户提问时快速找出最相近的片段。向量数据库就是为这件事提供的数据层。本篇使用 Chroma 介绍集合、向量、文档和元数据的关系,并用预先写好的小向量完成一次无需模型 API 的本地检索;这样可以先验证检索流程,再接入真正的 Embedding 服务。
向量数据库解决什么问题
普通数据库擅长精确条件,例如 section = '安装' 或 id = 42。向量数据库则保存高维向量,并根据距离寻找“最相似”的记录。文本经过同一个 Embedding 模型编码后,意思相近的片段通常会落在向量空间中较近的位置,因此“如何配置缓存”可以召回没有使用完全相同词语的“缓存参数设置”。
一个最小记录通常有四部分:唯一的 id,用于相似度计算的 embedding,便于阅读或最终交给模型的 document,以及来源、版本、权限等 metadata。向量数据库的职责是存储、建立索引和返回候选片段;它不会自动判断答案是否正确,也不会替代权限检查和最终生成。
本篇选用 Chroma 的本地持久化客户端。官方 Python API 提供 PersistentClient、get_or_create_collection、add 和 query 等接口,适合先在单机上理解数据流。代码显式传入向量,不依赖默认 Embedding 模型下载,因此示例可以离线运行。
安装与最小检索程序
在项目自己的虚拟环境中安装依赖:
1 | python -m venv .venv |
下面的向量是教学用的二维坐标:第一维粗略表示“部署/运维”,第二维粗略表示“接口/开发”。真实项目不能手工指定它们,而应使用同一个 Embedding 模型编码入库文本和查询文本。
1 | from pathlib import Path |
运行脚本后,返回的两个候选应优先接近第一条和第三条记录。这里的 distance 是距离,通常数值越小表示越相近;不要把它直接当成百分比或“答案正确率”。返回结果按相似度排序,外层列表对应一次查询,内层列表对应这次查询的 n_results 条结果。
PersistentClient 会把数据写入指定目录,所以进程退出后仍可重新打开。get_or_create_collection 避免重复初始化集合;add 要求每条记录有稳定且不重复的 ID。生产导入时,建议使用文档版本或内容哈希生成 ID,这样可以明确处理更新和去重,而不是随机生成后无法定位旧数据。
从示例向真实 Embedding 过渡
实际流程可以拆成四步:先读取原文并按上一课的规则切分;再调用 Embedding API 为每个片段生成向量;把向量、正文和元数据批量写入集合;收到用户问题后,用同一个模型生成查询向量并调用 query。入库和查询必须使用相同的向量空间,不能用模型 A 写入、模型 B 查询而不做迁移验证。
本地原型可以显式传入 embeddings,从而完全控制向量化过程;如果让 Chroma 根据 documents 自动生成向量,则要确认当前客户端使用的 Embedding 函数、模型文件和网络行为,并在部署环境中固定版本。无论选择哪种方式,都应把模型名称、维度和版本记录到集合或数据处理配置中。向量维度不一致时,写入或查询会失败;模型升级后也不应悄悄混用新旧向量。
检索结果交给生成模型前,还要做两项工作。第一,按租户、权限和文档版本过滤元数据,不能先召回敏感内容再让模型“自行忽略”。第二,保留 source、章节和片段序号,最终回答时展示可追溯引用。向量检索只是召回候选,不是事实核验;对关键业务仍应增加阈值、重排或人工确认。
常见问题
为什么不用关键词搜索? 关键词搜索对专有名词、错误码和精确短语很有优势,向量搜索对改写和同义表达更有优势。实际系统常把两者结合,而不是认为向量检索可以替代所有搜索。
n_results 设置得越大越好吗? 不是。结果太少可能漏掉证据,太多会带入噪声并占用上下文。应使用一组已知问题和期望片段测试召回数量,再决定默认值。
为什么相似片段没有被召回? 先确认入库文本与查询文本经过同一模型编码,再检查切分边界、元数据过滤、距离度量和查询向量维度。不要一看到错误答案就直接改提示词,召回阶段可能根本没有提供正确片段。
示例为什么删除数据库目录? 为了让脚本重复运行时结果确定。真实程序不应在启动时删除持久化目录,而应使用稳定集合名、稳定 ID 和明确的增量更新策略。
小结
向量数据库的核心不是“替模型回答”,而是保存向量及其可追溯信息,并按距离返回相似候选。本文用 Chroma 的本地持久化客户端完成了创建集合、写入向量、保存元数据和查询结果的最小闭环。教学向量验证的是数据库操作流程;接入真实项目时,还要补上统一的 Embedding 模型、版本管理、权限过滤、召回评估和引用展示。下一步可以在此基础上学习如何构建一个完整的本地 RAG 问答程序。