做了半年RAG知识库,我有个深刻的教训:很多人以为RAG答得不准是LLM的问题,其实七八成出在Embedding和检索上。我最早用默认Embedding模型跑知识库,检索出来的内容经常驴唇不对马嘴;后来系统性地做了一轮Embedding选型和检索调优,检索准确率翻了一倍,知识库问答质量肉眼可见地提升。这篇文章把选型和调优过程完整记录下来。
RAG的流程是"用户问题→检索→把检索结果给LLM→生成回答"。其中"检索"这一步的质量,直接决定LLM"吃到的材料"对不对。而检索质量由三件事决定:
Embedding是地基,地基不牢,后面全白搭。
我测试了四个模型:bge-small-zh、bge-m3、text-embedding-v3(通义)、text-embedding-3(OpenAI),用我们自己的知识库文档+100个真实问题做评测。
模型 | 检索准确率(top5) | 速度 | 成本/部署 |
|---|---|---|---|
bge-small-zh | 61% | 快 | 免费,本地跑 |
bge-m3 | 79% | 较快 | 免费,本地跑 |
text-embedding-v3 | 82% | 快 | API计费 |
text-embedding-3 | 80% | 快 | API计费 |
结论:bge-m3和两个云端模型差距很小(2-3个点),考虑到免费、本地部署、数据不出内网,我们最终选了 bge-m3——性价比之王。这个结果也印证了:对中文内部文档,国产开源Embedding模型已经够用,没必要迷信云端大牌。
我的评测不是拿网上的标准数据集,而是用自己业务里真实的100个问题+知识库文档测。因为Embedding的好坏高度依赖领域——通用评测分数高,不代表在你的文档上就准。这个教训很重要,很多团队拿通用基准选模型,上线后才发现不匹配。
我把同一个文档用三种方式切分对比:
按语义段落切分效果最好——因为文档的语义单位本来就是"段",切开后每块内容是完整的。实现上,我按Markdown标题把文档拆成"章节块",块太大再按句号二次切分。
纯向量检索对"关键词精确匹配"不敏感(比如搜"发票号"容易漏)。我加了BM25关键词检索,把向量分数和关键词分数加权融合。加上后,术语密集的场景准确率又提升了5个点左右。
用户的问题往往很口语化("报销咋弄"),和文档里的书面表述向量距离远。我先让LLM把问题"改写"成更规范的表述("报销流程是什么"),再拿去检索,命中率明显提升。这个小改动,效果立竿见影。
这次调优的总收益:检索准确率从61%提到82%+,知识库问答的"答非所问"明显减少。我的心得总结三条:
如果你也在做RAG且觉得"答得不准",先别急着换大模型——把Embedding、切分、检索这三层从头调一遍,很可能花半天时间就能让质量上一个台阶。