这道题问的是为什么[[RAG]]里要分召回和[[重排序]]两步走,而不是让重排序一步到位。其实本质就是在问计算成本和精度之间的权衡。如果直接用 [[Cross-Encoder]] 这种重型模型去扫百万级文档,计算量会大到没法接受,延迟和成本都扛不住,所以必须拆成两阶段,先快速捞一把,再精细排一遍。
具体说一下。召回阶段,比如用 [[BM25]] 或者 向量检索,目标是快,从海量文档里筛出几百上千个候选,这个阶段模型很轻量,延迟能控制在毫秒级。重排序阶段,候选集已经很小了,就可以上 Cross-Encoder 这种精细模型,让 query 和文档做深度的交互计算,把最相关的排到前面。召回是保召回率,重排是提精度,缺一不可。
举个例子,在客服退款场景里,用户问“为什么我的退款还没到账”,召回阶段可能从百万条知识库里捞出几百条跟退款流程相关的文档,重排阶段再根据用户的具体描述,比如“已提交三天”,把最匹配的那几条排到最前面,这样 LLM 才能给出准确回复。如果只用召回,可能排在前面的都是泛泛的退款政策,不精准;如果只用重排,那延迟就爆炸了,用户等不了。
这个架构的好处很明显:效率可控,召回快,重排只处理小量数据;精度能提上去,因为重排模型能捕捉细粒度语义;而且召回和重排可以独立优化,比如换个更好的 [[Embedding]] 模型或者换一个重排器。但缺点也得心里有数。最核心的风险是误差累积,如果召回阶段把重要文档漏掉了,重排阶段再怎么排也找不回来,这就是召回率天花板。另外系统复杂度上去了,要维护两套索引和两个模型,运维成本高;而且两阶段串行,总延迟是叠加的,对实时性要求特别高的场景需要注意。
所以实际落地时,我会特别关注召回阶段的质量,比如用 [[Hybrid Search]] 把 [[稀疏检索]] 和 [[稠密检索]] 结合起来,降低漏召回的风险。如果对延迟特别敏感,可以换成 [[ColBERT]] 这种轻量交互模型做重排,或者把召回阶段做得更激进一点,比如只保留 Top-100。上线前我会用一批线上真实 query 做 A/B 测试,看召回率和最终回答质量有没有掉,如果掉就调召回策略。
另外还有一个有意思的点,就是召回和重排的边界其实可以灵活调整。比如在 [[Agentic RAG]] 里,[[Agent]] 可以动态决定是继续召回还是直接重排,甚至多次迭代。这个方向其实挺值得深入聊的。
所以整体上,两阶段架构是个很务实的工程选择,核心就是在成本和精度之间找到平衡点。我更倾向把它看作一个可调节的 pipeline,而不是固定的套路,根据业务场景去调召回量和重排模型,才能落地得稳。