这道题其实问的是[[RAG]]里一个非常实际的问题,检索模块拿回来的东西不对,生成就会跑偏。本质上这是个链路级匹配失败,不是单一环节的锅,所以修也要从检索、[[重排]]到生成系统性修。
先分析原因。最典型的场景,比如电商客服系统里用户查“充电宝上飞机”,用户问的是民航规定,但检索可能因为[[embedding]]相似度高,把一堆充电宝产品介绍和评测文召回来,这些文档语义上相关但事实无关,生成器一综合就可能给出矛盾信息。这里原因有三层:查询侧,用户query太短或者有歧义,embedding抓不到真实意图;索引侧,文档切分不好,关键信息被截断,或者原文档本身质量参差,有过期的、矛盾的;匹配侧,向量检索的语义相似不等于事实相关,这是最根本的坑。
解决方案我分三层讲。第一层检索优化。**[[混合检索]]**是标配,把向量检索和关键词检索结合起来,比如用户问“充电宝”而文档里写的“移动电源”,向量能兜住同义,但关键词能精准匹配订单号、错误码这类精确信息。再一个就是查询扩展,用LLM把用户query做同义改写或拆成子问题,多路检索再融合。不过这里有个前提:索引质量得过关,如果文档本身质量差,切分策略不对,检索再好也没用。我一般会用语义滑窗切分,再加实体提取做辅助索引。
第二层重排序。检索完拿到topK文档后,别直接用,先过一遍重排。**[[交叉编码器]]**比双编码器精度高很多,因为它算query和文档的细粒度交互,能抓到字面匹配信号。但交叉编码器慢,所以我会做级联,先用轻量模型粗筛到top100,再用重模型精排到top5。这样既保精度又控延迟。但重排也有边界:如果检索出来的文档本身全是噪声,重排也救不了,它只能从好文档里挑更好的。
第三层生成控制。这是最后一道防线。我会加一个置信度门控,如果检索文档和query的相似度低于某个阈值,直接触发“知识不足”提示,让模型说不知道而不是瞎编。还有证据验证,要求模型生成时显式引用文档片段,再用NLI模型检查生成内容跟证据是否一致。如果多文档结论冲突,就让模型输出“存在不同说法”并列出依据,别强行综合。
这里有个值得深挖的点:重排序的模型选择很大程度上决定了整个链路的精度天花板。如果重排模型本身在领域数据上没做过微调,那即使检索召回率很高,重排也可能把好文档排到后面。所以落地时我会特别关注重排模型的领域适配,比如用领域内的query-doc对做继续训练。
最后说下我的取舍。如果资源有限,我会把重排序作为标配,因为它性价比最高,在不改检索和生成的情况下,能直接提升topK质量。生成端的控制更多是做兜底,防止极端情况。但整体上,我更倾向把RAG看成一个可控降级系统,偏差无法完全消除,核心是让模型在检索失败时知道不知道,而不是强行编造。