Skip to content

RAG 检索优化:距离、稀疏稠密、粗排精排与向量数据库

面试结论| 生产检索通常不是“向量库搜 TopK”一个动作,而是硬过滤后由 BM25/稀疏检索守住精确词,由稠密向量补充语义召回,再用 RRF 或归一化加权融合,最后让 Cross-Encoder 在有限候选上精排。粗排负责低成本扩大 Recall,精排负责在候选内提高前排 Precision;向量数据库只提供存储、索引、过滤与查询能力,不能替代数据治理、评测和排序策略。

目录

1. 小白先这样理解

小白先这样理解:给走失宠物匹配线索

社区里一只叫“雪球”的白色柴犬走失。志愿者收到四条线索:

  1. “看到名牌写着 XQ-204 的白色柴犬”;
  2. “公园里有只浅色中型犬,一直追红色飞盘”;
  3. “宠物店见到白色萨摩耶”;
  4. “停车场有只棕色柯基”。

按编号查找时,第 1 条最可靠;按描述含义找时,第 2 条也很值得调查。系统先让两支便宜快速的队伍工作:一支按名字、编号和词语查,另一支按整体语义查;合并出几十条候选后,再让熟悉犬种和上下文的专家逐条比较“问题 + 线索”,排出最终顺序。

故事元素技术概念边界
XQ-204、名字、犬种查精确匹配、倒排索引、BM25/稀疏检索词面不重合时可能漏掉
按“浅色中型犬追红飞盘”找相似描述稠密向量、语义相关性可能把语义相近但事实不同的线索排高
两队各交一批名单多路粗排与各自 k_recall只保证候选,不保证最终顺序
合并名单RRF 或归一化加权融合异构原始分数不能随便相加
专家同时阅读寻犬信息与线索Cross-Encoder 精排计算贵,且救不回未召回线索

类比边界: 专家可能凭现实经验核验颜色、时间和地点,模型只依据训练与输入。若元数据时间范围、地理范围或权限没有作为硬约束,相关性再高也可能是错误候选。

2. 一张数据表看懂完整漏斗

示例查询:企业版 ERR-42 付款一直转圈怎么办?

阶段输入规模代表动作示例输出主要目标
硬过滤100 万 Chunktenant=17 AND product=enterprise AND version=v78 万可见 Chunk正确边界
BM25 粗排8 万匹配 ERR-42、企业版、付款100 个候选精确词召回
Dense 粗排8 万匹配“支付卡住/结算无响应”语义100 个候选语义召回
融合去重最多 200stable ID 去重,RRF60 个候选汇总互补信号
Cross-Encoder 精排60联合编码 Query 与 Chunk前 12 个前排相关性
上下文选择12去重、父块扩展、Token 预算5 个证据块可生成证据

表中数字是演示漏斗,不是推荐参数或实测数据。生产上应明确维护:

text
k_recall_sparse, k_recall_dense > k_rerank >= k_context

这里表达阶段关系,不代表必须使用某个固定数值。

3. 欧几里得距离、余弦相似度与点积

3.1 先纠正术语

“余弦定理”是三角形边角关系;向量检索常用的是余弦相似度(Cosine Similarity),它可由向量夹角定义,并能联系到余弦定理,但两者不是同一个检索算法名称。

若三角形两边长度为 a,b,夹角为 θ,对边为 c,余弦定理是:

c2=a2+b22abcosθ

把两条边看成从原点出发的向量 x,y,则 a=xb=yc=xy。与 xy2=x2+y22xy 对照,可得 xy=xycosθ,再归一化就是余弦相似度。余弦定理提供几何关系,余弦相似度才是检索中用于比较向量方向的量。

3.2 欧几里得距离

对向量 x,yRn

dL2(x,y)=i=1n(xiyi)2

距离越小越相近。它同时受方向和模长影响,适合模长具有明确意义或模型按 L2 空间训练的表示。

生活直觉是城市地图上的直线距离:两家店坐标越近,走向上越相似。但高维语义空间不是物理地图,维度由模型学习,不能把单维直接解释为“价格”或“情绪”。

3.3 余弦相似度

cos(x,y)=xyx2y2

它主要比较方向;值越大通常越相似。若向量都已归一化为单位长度:

xy22=22cos(x,y)

因此在单位向量上,按 L2 距离与按余弦相似度排序等价。这个结论依赖相同的归一化条件

3.4 点积

sdot(x,y)=xy

点积同时受方向和模长影响。若向量均已单位归一化,点积等于余弦相似度;未归一化时,不能把两者混称。

3.5 用二维数据手算

设 Query q=(1,1),三个文档向量:

  • a=(2,2):方向完全相同但模长更大;
  • b=(1,0):部分同向;
  • c=(1,1):方向相反。
文档L2 距离,越小越好余弦,越大越好点积,越大越好
a21.41414
b11/20.7071
c222.82812

这里余弦认为 a 与 q 方向完全一致,L2 却认为 b 在坐标位置上更近。选择距离度量必须服从 Embedding 模型训练与官方建议,并在目标数据上验证,不能凭习惯切换。

4. 倒排索引、倒排排名与 BM25

4.1 什么是倒排索引

正排索引是“文档 → 包含哪些词”,倒排索引是“词 → 出现在哪些文档、哪些位置”。例如:

text
ERR-42 -> [(doc_1, tf=2, positions=[3, 19]), (doc_7, tf=1, positions=[8])]
付款   -> [(doc_1, tf=1), (doc_3, tf=4)]

查询不必扫描全库文本,而是从词项的 posting list 取得候选。所谓“倒排排名”不是一种与 BM25 并列的固定算法,更准确的说法是:倒排索引负责快速找候选,BM25 等相关性函数负责排序

4.2 精确匹配不等于 BM25

  • 精确匹配可以是 ID、Keyword 字段、短语、布尔条件或未分词字段的相等判断;
  • BM25 是基于词项统计的软相关性排序;
  • 版本号、订单号、错误码常需要 keyword/phrase/field filter,不能只依赖默认分词后的 BM25;
  • 中文还需要选择分词器、词典、同义词和字段策略,否则“企业版”可能被不合适地拆分。

4.3 BM25 核心公式

一种常见写法为:

score(D,Q)=qiQIDF(qi)f(qi,D)(k1+1)f(qi,D)+k1(1b+b|D|avgdl)
  • f(qi,D):词 qi 在文档 D 中的频次;
  • IDF(qi):词越稀有,区分力通常越强;
  • k1:控制词频饱和,出现 20 次不会简单等于出现 1 次的 20 倍;
  • b:控制文档长度归一化;
  • |D|/avgdl:当前文档长度相对平均长度。

4.4 小数据直觉

在 1000 篇文档中,“系统”出现于 900 篇,“ERR-42”只出现于 3 篇。查询包含两词时,ERR-42 的 IDF 区分力更强;但若某篇文档把 ERR-42 重复堆砌 100 次,词频饱和会限制刷分。

BM25 擅长错误码、函数名、产品名、法规条款和精确术语;它不理解词面完全不同的“付款一直转圈”与“支付请求未完成”可能同义。

5. 稀疏、稠密、语义相关性与精确匹配

5.1 稀疏向量

稀疏(Sparse)表示维度很高,但大多数值为零。传统词袋/BM25 可视作以词项为维度的稀疏信号;SPLADE 一类学习式稀疏模型还能扩展相关词,但仍保留可解释词项维度。

5.2 稠密向量

稠密(Dense)表示维度相对固定且多数值非零。Embedding 模型将文本、图像或音频映射到连续空间,用向量距离近似语义相关性。

5.3 四种相关性不要混成一个词

信号它回答什么擅长典型误判
精确匹配字符/字段是否相等或包含ID、错误码、版本、短语同义改写完全不重合
词法相关性查询词在文档中多重要名词、术语、可解释搜索只看词面,不懂完整意图
向量语义相关性表示空间中是否接近同义表达、自然语言描述语义相近但事实、主体或时间错误
任务相关性这段证据是否真正回答当前问题条件、否定、细粒度关系需要联合读 Query 与文档,成本高

Cross-Encoder 更接近第四类,但仍不是事实验证器。

6. TopK、粗排、融合与精排

6.1 TopK 是一个操作,不是一个固定参数

TopK 表示按某个分数/距离取前 K 个。RAG 中至少有:

  • k_recall_sparse:BM25/稀疏路候选数;
  • k_recall_dense:向量路候选数;
  • k_fusion:融合后保留数;
  • k_rerank:送入精排模型的候选数;
  • k_context:最终进入上下文的证据数。

只说“TopK=5”没有说明阶段、分母、Token 预算和评测目标,几乎无法判断是否合理。

6.2 粗排与精排

粗排(Candidate Retrieval/First-stage Ranking)面向大语料,用倒排或 ANN 等索引快速缩小候选。它追求较高 Recall、较低单候选成本与稳定延迟。

精排(Reranking/Second-stage Ranking)只处理几十或几百候选,使用更贵、更细的 Query-Document 交互提高前排 Precision。精排不能补回粗排没有召回的证据。

6.3 为什么不能直接对全库 Cross-Encoder

若有 100 万 Chunk,每次都把 Query 与全部 Chunk 联合编码,计算和延迟通常不可接受;而双塔 Dense 可预计算文档向量,在线只编码 Query 并做 ANN。两阶段本质是缓存可复用表示换速度,再用少量深交互换精度

7. Cross-Encoder 与加权

7.1 Bi-Encoder 与 Cross-Encoder

维度Bi-Encoder/双塔Cross-Encoder/交叉编码器
输入方式Query 与文档分别编码[Query; Document] 联合编码
文档表示可离线预计算通常每次 Query 都要重算配对
速度适合全库粗排适合有限候选精排
交互强度压缩成单向量后比较Token 级联合注意力更充分
边界可能丢细粒度关系成本高、输入截断、不能补召回

7.2 加权的三种位置

  1. 检索融合权重: Sparse 与 Dense 的贡献;
  2. 业务排序权重: 权威性、新鲜度、地域等软信号;
  3. 多模态权重: 文本、图像、音频等不同向量空间的贡献。

最危险的写法是直接:

text
final = 0.5 * bm25_raw_score + 0.5 * cosine_score

BM25 分数通常无统一上界,余弦的范围和分布又由模型决定,原始分数尺度不同且会随 Query 漂移。更稳妥的起点:

  • 用 RRF 按名次融合,不依赖原始分数可比;
  • 或先在每路做可靠归一化/校准,再用验证集学习权重;
  • 业务 boost 应有上限,不能让热度压过基本相关性;
  • 权重必须分查询类型评测,不用一套 α 覆盖错误码、自然语言和版本查询。

RRF 常见形式:

RRF(d)=rRwrc+rankr(d)

它稳健但会丢失分数幅度;若第一名和第二名原分数差距巨大,RRF 只看到名次差。

8. 向量数据库与关系型数据库

8.1 向量数据库是什么

向量数据库或向量搜索引擎围绕高维向量的近邻搜索优化,常提供 HNSW/IVF 等 ANN 索引、距离度量、元数据过滤、分片复制、批量写入和混合检索能力。

8.2 关系型数据库是什么

关系型数据库围绕表、Schema、约束、事务、JOIN、精确查询和一致性构建。pgvector 说明两者不是互斥物种:PostgreSQL 可以通过扩展获得向量类型和 HNSW/IVFFlat 搜索,在一套事务与 SQL 中同时管理业务字段和向量。

8.3 核心区别

维度专用向量引擎关系型数据库设计判断
主查询高维相似度/ANN精确过滤、JOIN、聚合、事务看核心负载,不看名称
一致性与事务产品差异大,常重搜索吞吐成熟 ACID 与约束业务真值优先留关系库
Schema/关系Metadata 过滤为主复杂关系和查询优化成熟多表业务逻辑不应硬塞向量库
扩展方式分片、索引、向量压缩专门优化通用数据库扩展,向量能力依实现规模与运维能力决定
混合检索有的原生支持稀疏/混合可配 FTS + pgvector用同一评测集比较
运维边界新系统、新备份与一致性模型可复用现有 Postgres 能力小规模先避免过度拆分

关键边界: 向量库通常不是订单、权限、价格和账户余额的业务真值库。常见架构是关系库存文档状态与权限真值,向量引擎存可重建的检索投影,通过 outbox/CDC/任务对账保证同步。

9. 向量检索产品横向对比

事实边界| 下表依据各产品官方资料在 2026-07-13 可见的能力说明整理,只证明能力候选,不证明在你的数据、规模、硬件和团队约束下谁更优。价格、托管区域、版本限制和性能必须发布前重新核对并实测。

候选定位与能力侧重优点代价/风险更适合不宜仅凭此选择
pgvectorPostgreSQL 扩展;精确检索、HNSW、IVFFlat,可与 FTS 组合复用 SQL、事务、备份与业务数据;架构简单超大规模向量负载与独立扩缩容需实测;ANN 过滤要调参已有 Postgres、中小规模、强事务/过滤只因“少一个组件”就忽略容量与 P99
Elasticsearch倒排、BM25、过滤与 kNN/混合检索统一在搜索引擎词法搜索、字段查询、分析器和可观测生态成熟集群与映射运维复杂,向量成本需压测搜索本来就是核心、精确词与语义并重只做简单向量 PoC
Qdrant向量搜索;named dense/sparse/multivector、过滤、多阶段查询混合与多阶段查询表达清晰,Payload 过滤与多向量友好复杂全文分析能力边界与 Elastic 不同;需新增服务治理向量优先、混合/多向量、希望自托管或云把它当复杂关系/全文分析数据库
Milvus分布式向量数据库;多向量、过滤、混合搜索面向大规模向量和多种索引/部署形态组件、容量规划和运维复杂度较高大规模、独立向量平台、专业运维团队小数据且团队不愿承担平台成本
Weaviate对象/向量搜索;BM25F、向量、混合、过滤、named vectors混合搜索接口完整,Schema 与模块生态丰富版本特性、模块和资源模型需核对希望一体化对象+混合搜索不做版本验证就依赖预览能力
Pinecone托管向量服务;Dense/Sparse/Hybrid、Metadata、Namespace托管运维、快速交付、弹性服务厂商依赖、费用、数据区域与一致性边界需评估不想自建集群、重视交付速度强本地部署、特殊合规或需完全控制底层
Chroma/本地轻量方案开发与本地向量检索上手快、适合教学和原型生产扩展、HA、治理能力需单独验证Notebook、单机 PoC、测试仅凭 PoC 顺畅直接作为大规模生产结论

9.1 条件式选型路径

  • 数据与业务事务强绑定、规模可控:先验证 PostgreSQL + pgvector;
  • 已有成熟 Elastic 搜索集群,错误码/字段/全文检索占比高:优先验证 Elastic 混合检索;
  • 向量、多向量、过滤与自托管是核心:比较 Qdrant、Milvus、Weaviate;
  • 团队希望托管、快速上线:评估 Pinecone 等托管方案,同时核对区域、费用、导出与锁定风险;
  • 教学/原型:轻量本地方案可以最快闭环,但生产结论必须重新评估。

10. 技术点清单与横向选型

技术点 ID技术点/环节类型采用方案链路职责版本/证据边界
TP-R01词法粗排检索算法倒排索引 + BM25 + 精确字段召回编号、术语和词面证据Analyzer 与参数按语料验证
TP-R02语义粗排模型/索引Dense Embedding + ANN召回同义和意图相近证据距离度量服从模型说明
TP-R03融合排序算法RRF 起步,受控数据再校准加权合并异构候选权重与常数无通用最优
TP-R04精排模型服务Cross-Encoder联合判断 Query-Chunk 任务相关性只覆盖已召回候选
TP-R05向量存储数据基础设施依规模、事务、运维和搜索负载选型存向量/Metadata 并执行过滤与 ANN官方能力核对于 2026-07-13
技术点 ID候选方案优点缺点/代价适用场景不适用场景选择结论与依据
TP-R01精确 Keyword/Phrase确定、可解释无同义召回ID、版本、错误码自然语言改写与 BM25 并存
TP-R01BM25/BM25F词频统计和字段权重成熟依赖分词,语义弱技术文档、专名纯语义问法词法默认基线
TP-R02精确 KNNRecall 可作为 ANN 基线全库成本高小库、离线校验大规模低延迟用于基线与抽样审计
TP-R02HNSW/IVF 等 ANN速度和规模更好牺牲部分 Recall、需调参生产大库不能容忍近似误差用精确检索测 ANN Recall
TP-R03RRF不依赖异构原始分数尺度丢分数幅度信息无可靠校准的多路检索需要精细概率解释稳健起点
TP-R03归一化/学习加权可利用分数与查询特征需标注集、校准和防漂移有充足评测数据无标注或尺度不稳证据充足再升级
TP-R04Bi-Encoder 相似度快,可预计算交互不足粗排最终细粒度排序不替代精排
TP-R04Cross-Encoder联合交互更充分延迟、成本、截断有限候选精排全库扫描配超时降级
TP-R05关系库扩展事务与 SQL 复用独立扩缩和极限规模需验证强业务关系、中小规模纯向量超大负载先做成本最低基线
TP-R05专用/托管向量引擎ANN、分片、多向量能力集中新系统、成本和锁定向量为核心负载简单 PoC按受控基准选,不按榜单选

11. 架构、调用流程与最小实现

图:架构|混合检索、粗排精排与双存储边界

替代文本: 关系库存放权限、文档状态和版本真值,搜索/向量索引保存可重建投影;查询编排先生成可信硬过滤,再并行调用 BM25 与 Dense 粗排,融合去重后由 Cross-Encoder 精排并选择上下文,Trace 记录每层候选与版本。

图表加载中…

读图结论: 业务真值和检索投影职责不同;相关性优化只能发生在受权候选内,每个排序阶段都必须可重放。

图:技术调用流程|一次混合检索的成功、超时与降级

替代文本: 编排器先校验身份并构造硬过滤,并行请求词法和向量粗排;一路超时可在受权结果内降级,两路都失败则拒绝无证据回答;融合候选送精排,精排超时退回融合排名,最终二次授权并记录上下文。

图表加载中…

读图结论: 允许降级的是相关性质量,不允许降级的是权限边界;两路都没有可靠证据时应拒答,而不是让模型凭参数记忆补全。

最小融合伪代码:

python
def rrf(rank_lists, weights=None, c=60):
    weights = weights or [1.0] * len(rank_lists)
    scores = {}
    for weight, docs in zip(weights, rank_lists):
        for rank, doc in enumerate(docs, start=1):
            scores[doc.stable_id] = scores.get(doc.stable_id, 0.0) + weight / (c + rank)
    return sorted(scores, key=scores.get, reverse=True)

# 仅示意:c=60 不是通用最优值;必须保存每路原 rank 与检索版本。

12. 排障、面试追问与总结

12.1 正确证据首次消失在哪一层

现象对比数据首要假设
BM25 无、Dense 有分词 Token、词项 DF、Dense rank同义表达或 Analyzer 问题
Dense 无、BM25 有向量范数、模型/维度、距离分布Embedding/索引版本错或专名 OOV
两路有、融合后掉出各路 rank、stable ID、融合配置候选深度不足、重复、权重/RRF 配置
融合有、精排后掉出输入是否截断、Reranker 版本与分数精排模型不适配、截断或版本漂移
精排有、上下文没有k_context、父块、去重、Token 截断上下文选择错误

12.2 递进追问

  1. 单位归一化后,L2、余弦和点积的排序关系是什么?
  2. 倒排索引与 BM25 分别负责什么?
  3. 为什么“语义相关”不等于“事实正确并能回答问题”?
  4. 为什么 BM25 原始分数不能和余弦分数直接加权?
  5. Cross-Encoder 为什么只能精排,不能补召回?
  6. 什么时候 pgvector 比专用向量库更合适,什么时候应拆分?
  7. 如何用精确 KNN 评估 ANN Recall 与参数取舍?

12.3 一分钟面试复述版

我把检索拆成硬过滤、两路粗排、融合、精排和上下文选择。BM25 基于倒排与词项统计,擅长错误码和精确术语;Dense 用向量空间补同义和意图召回,距离度量必须服从模型训练与归一化方式。两路原始分数尺度不同,我通常先用 RRF,再在有标注集时做校准加权;Cross-Encoder 只处理有限候选,提高前排相关性,但救不回漏召回。向量数据库选型要同时看规模、过滤、混合检索、事务、运维、合规和成本,小规模强事务场景可先验证 pgvector,专用引擎则要用相同数据和 SLO 压测。

参考资料

简明总结

一句话记忆: 粗排负责“别漏”,精排负责“排对”,硬过滤负责“不能错看”,数据库负责“高效执行”而不是替你决定答案。

  • 欧几里得、余弦和点积只有在明确归一化条件下才能讨论排序等价;
  • 倒排索引找候选,BM25 排词法相关性,精确字段守住编号与版本;
  • Sparse 与 Dense 互补,语义相关不等于事实正确;
  • 多个 TopK 分属召回、融合、精排和上下文,必须分开记录与调优;
  • 向量库与关系库不是替代关系,选型取决于真实负载、事务、规模和团队边界。