933 字
约 3 分钟
8
S13-A02 · 语义搜索与混合检索:BM25 + kNN

适用读者:被"要不要上向量检索"困住的人。
前置:S13-A01。
覆盖旧文:563(585) 636(78) 637(84) = 747 点。
覆盖扩展:E-S13-011(BM25 vs 向量)、E-S13-012(topK 与重排)。
上一篇:S13-A01 · MySQL → ES 同步:全量、增量与一致性
下一篇:S13-A03 · 向量库选型。


1. 一句话结论

BM25 匹配"字面",向量匹配"语义"。两者都不完美:字面匹配不懂同义词,语义匹配不懂精确词。混合检索就是"两路召回 + 重排"。

方式 强项 弱项
BM25(关键词) 精确词、专有名词、可解释 同义词、口语化表达
向量(kNN) 语义相近、跨语言 精确词、数字、代号
混合 兼顾 复杂度与成本上升

2. 什么时候值得上语义检索

场景 建议
商品/内容搜索,用户表达多样 ✅ 值得
代码/日志/ID 搜索 ❌ 关键词足够
客服问答(同义问法多) ✅ 值得
数据量小、词表固定 ❌ 别过度设计

判据:"用户的实际输入和文档用词,重合度高吗?" 高 → BM25 够;低 → 需要语义。


3. 混合检索的架构(E-S13-011)

查询
 ├─ BM25 召回 topK1(关键词)
 ├─ kNN 召回 topK2(向量)
 └─ 合并 + 重排(RRF / 加权 / 交叉编码器)
        ↓
     最终 topN
合并方式 说明
RRF(倒数排名融合) 只看排名,不需归一化分数(简单稳健)
加权分数 需归一化(BM25 与余弦相似度量纲不同)
重排模型 精度最高、成本最高

"为什么用 RRF":两种检索的分数不可比(BM25 无上界、cos 在 −1..1),直接相加会偏。


4. topK 与重排(E-S13-012)

阶段 典型 K 目的
召回 50–200 保证召回率
重排 10–20 保证精度
展示 10 用户体验

"召回大、重排小"是标准范式——召回阶段宁可多、重排阶段才精。


5. ES 里的实现要点

能力 ES 8 的做法
向量字段 dense_vector(dims + similarity)
kNN 查询 knn 子句(近似检索)
混合 knn + query 同时给(ES 8.4+ 原生支持)
重排 应用层或 rerank(视版本/插件,待核)

注意:向量检索的内存开销远大于 BM25(HNSW 索引常驻内存)。


6. 五个误区

误区 真相
"向量检索能替代关键词" 精确词/数字它是弱项
"混合一定更好" 成本与复杂度上升
"分数可以直接相加" 量纲不同,需 RRF/归一化
"topK 越大越好" 延迟与噪声上升
"上了向量就不用分词" 关键词路仍需要

7. 自检(架构师版)

  1. BM25 与向量的强弱项?
  2. 什么场景不值得上语义检索?
  3. 混合检索的三步?
  4. 为什么用 RRF 而不是分数相加?
  5. 召回 K 与重排 K 的典型值?

8. 下一篇

S13-A03 · 向量库选型:ES vs 专用向量库

混合检索讲完,下一篇做选型:一套 ES 还是再加一套向量库。


本篇属于系列《S13 · 搜索与文档存储》。旧文来源:A-563/636/637;扩展点 E-S13-011/012。

S13-A02 · 语义搜索与混合检索:BM25 + kNN
https://www.clxhxhhr.top/posts/5367/
作者
clxstart
发布于
2024-12-31
许可协议
CC BY-NC-SA 4.0
评论
0 条
还没有评论,先写一条吧。