做Agent开发的,RAG是绕不开的一道坎。不管是让大模型读懂企业的私有文档,还是给智能体补上“实时知识”这一课,RAG(Retrieval-Augmented Generation,检索增强生成)都是当前最主流、也最容易落地的方案。这篇笔记是我在Agent开发学习路上整理的第七篇,专门把RAG从建库到检索再到生成的完整链路拆开讲一遍,包含我个人踩过的坑和实测下来的优化细节。内容偏工程实践,适合正在做Agent项目、或者准备给自己的产品接入私有知识库的朋友。
本文的目的是帮你建立一条从“原始文档”到“可用问答”的完整通路。核心会围绕三个问题展开:怎么把乱七八糟的文档变成机器能检索的知识库?怎么从知识库里又快又准地把相关内容捞出来?捞出来之后怎么让大模型基于这些内容生成靠谱的回答?在这个过程中,我会穿插讲清楚嵌入模型、向量数据库、切片策略、混合检索、重排序等关键组件为什么存在、什么时候用、怎么搭配,避免你照着网上的碎片教程拼出一个能跑但不好用的玩具。
1. 想清楚再动手:RAG到底解决的是什么问题
1.1 大模型的“知识短板”与RAG的解题思路
大模型本质上是一个“参数化记忆”系统——它知道的都来自训练数据,知识截止在某个时间点,而且当你问的是企业的内部制度、产品的私有规格、某个特定领域的冷门细节时,它大概率会一本正经地“编”。我之前专门测试过,让GPT-4o回答一份内部技术规范里才有的字段定义,它给出的答案结构完整、语气笃定,但内容是纯幻觉。这就是RAG要解决的核心问题:用外部检索到的真实信息,去约束和引导模型生成。
RAG的思路其实很简单,像一个开卷考试:大模型不再凭记忆闭卷答题,而是先给你一本“参考书”(知识库),系统根据题目去参考书里找相关段落,再把找到的段落和题目一起交给大模型,让它基于这些材料作答。所以整个RAG系统就是三个环节:建库(把书写好)、检索(去书里找)、生成(看着书写答案)。
也正因为RAG的参考材料是可替换的,它天然适合做知识库更新:文档变了,重新建库或者增量更新即可,不需要重新训练模型。这在Agent场景里非常重要,因为Agent经常要对接用户上传的临时文件、企业实时更新的内部资料,模型不可能每次都重训。
1.2 RAG与Agent、MCP的边界与配合
最近总有人把RAG和MCP(Model Context Protocol)放在一起比较,我这边梳理一下:RAG是“把外部知识取回来给模型用”的一种技术范式,MCP是“让Agent能统一调用外部工具和数据源”的一种协议标准。两者不是替代关系,而是可以叠加的。在一个Agent项目里,RAG负责处理“非结构化知识”的召回(比如PDF文档里的规范、手册),MCP负责打通“结构化服务”的调用(比如查数据库、调业务API)。你可以把MCP看成Agent的手和脚,把RAG看成Agent的参考书架。
还有一个词叫Agentic RAG,本质上就是把RAG从“一次性检索”升级成“多步推理式检索”。传统RAG是你问一句、检索一次、生成一次;Agentic RAG是Agent自己判断需要先查哪个知识源、要不要拆解问题、要不要用检索结果再触发新一轮检索,来回几轮直到信息足够。这个我会在第五章详细展开。这里先记住一句话:RAG是整个链路的能力底座,Agent是调度策略,MCP是连接方式,它们各自解决不同层次的问题。
1.3 方案选型前必须明确的四件事
在动手建库之前,有四个问题必须先想清楚,它们直接决定技术选型。第一,语料的形态是什么?是纯文本、Markdown、PDF、Office文档,还是网页抓取下来的HTML?不同形态的预处理流程完全不同。第二,语料大概的量级是多少?几百篇和几百万篇,用的向量数据库、切片策略、检索方案都会不一样。第三,查询的类型是什么?是直接问某个事实(“公司报销上限是多少”),还是需要多文档交叉汇总(“比较A产品和B产品的参数”)?后者对检索和重排序的要求高得多。第四,系统对延迟和成本的要求?实时在线问答和离线分析对召回速度、模型规模的要求天差地别。
这些决定不做好的话,后面每改一步都要返工。我自己第一版RAG就是没想清楚量级,先用了一个本地文件+小型向量库的方案,结果语料涨到十万级之后检索延迟明显上头,整个检索层推倒重来,白白浪费了两周时间。所以这篇笔记的第一个建议就是:先花半天把场景和约束盘清楚,再动手写代码。
2. 建库:让“一本书”变成“一箱卡片”
2.1 文档加载与清洗:决定知识库质量的第一道工序
建库的第一步是把原始文档加载进来并清洗干净。这一步看着不起眼,实际上对最终检索质量的影响非常大。我做过一个统计:直接用未清洗的原始PDF切片建库,检索结果准确率比清洗后低了将近15个百分点。原因是PDF里经常有页眉页脚、水印、乱码断行,这些噪声被切进片段里之后,一方面会让向量化的语义被干扰,另一方面检索时如果命中了这些噪声块,模型拿到手的就是一堆垃圾输入。
清洗的常见处理包括:去掉页眉页脚和水印、修正PDF抽取过程中的断行拼接问题、去除多余空白字符和特殊符号、规范标点(尤其是把全角半角统一)、识别并保留表格结构(这个比较难,通常需要专用的文档解析模型,比如开源的一些表格识别工具)。对于HTML文档,还要去掉导航栏、广告、版权声明这类重复性噪音。说实话,文档解析和清洗环节最值得投入人力,市面上很多RAG项目效果不好,问题根源根本不在于模型和检索,而是喂进去的“原材料”就是脏的。
2.2 切片策略:切得不对,检索上限直接锁死
切片是RAG建库中最核心也最容易被低估的步骤。简单说,就是把长文档切割成适合检索和喂给模型的片段。切太碎,比如按每100个字硬切,会切断语义连贯的段落,导致检索到的内容上下文不完整,模型理解不了。切太大,比如整篇文章作为一个向量,检索时命中精度会很差,而且把大量不相关内容都塞进提示词里,既浪费token又稀释关键信息。
我实际测试过几种切片策略,简单总结如下。固定长度切片(比如每512个token切一刀,带少量重叠)实现最简单,适合结构松散的网页文本,但在语义连贯性上表现最差。按段落标题切利用文档原有的结构信息,对Markdown和结构化文档效果非常好,是我比较推荐的做法。递归字符切分是目前工程上综合效果最好的通用方案,思想是设定一个目标长度,然后按换行符、句号、空格逐级尝试切分,优先在语义边界处切开。语义切分是根据句子嵌入向量的变化幅度来判断断点,效果最好但计算开销大,适合语料质量要求极高的场景。
除了切片方式,切片大小也要定。我经验值是:通用知识问答场景单片段500~800个token比较合适;如果文档本身逻辑层层嵌套(比如法律合同、说明书),可以采用“父子切片”策略——父层级片段保留完整章节结构,子层级片段细粒度检索,检索到子片段后把父片段一起作为上下文喂给模型。这个策略能显著提升长上下文场景下的回答质量,缺点是建库复杂度高,向量存储会翻几倍。
2.3 嵌入模型与向量数据库选型
切片完成后,要将每个文本片段用嵌入模型(Embedding Model)转换成向量。嵌入模型的作用是“把一段文字变成一组数字”,这组数字要能表达语义:语义相近的文本在向量空间里的距离更近。选嵌入模型时最核心的关注点是三个:语义表征能力、向量维度、支持的语言和上下文长度。
语义表征能力可以用MTEB这类评测基准横向对比,不同模型的差距在专业领域语料上会被放大。向量维度影响存储和检索开销,常见的有384维(轻量级)、768维、1024维甚至更高。小项目、快速原型可以直接用OpenAI的text-embedding-3-small(1536维)或者更便宜的轻量开源模型;但如果涉及中文专业文档,我建议测试一下国产的几个中文优化模型,或者基于开源模型在自有语料上微调。有一点要特别注意:嵌入模型确定之后不要随意更换,因为不同模型生成的向量分布不同,更换后所有已入库数据都必须重新向量化,否则新旧向量会“互不识别”。
向量数据库的选型取决于规模、部署场景和运维能力。我按实际使用场景分类推荐:小规模本地原型(几万条向量以下)直接用开源的FAISS或者Chroma,轻量、零运维,但也别指望它的分布式和高级过滤能力;中大规模生产部署考虑Milvus或Qdrant,支持集合分区、丰富过滤、水平扩展;如果团队已经深度使用PostgreSQL,pgvector是一个能“少引入一个组件”的好方案,适合千万级以下的场景。挑选的时候不要光看性能Benchmark,要重点关注过滤能力(是否支持按元数据过滤后再检索)、混合检索支持度、部署复杂度、官方客户端语言覆盖这四个维度。
2.4 元数据设计:检索和后续处理的关键钩子
建库的另一件重要事情是元数据(Metadata)设计。很多人建库只图把文本切片向量化存进去,忽略了给每个片段打标签,这是后期制约检索质量的隐形瓶颈。元数据是什么?就是每个切片附带的描述性信息,比如来源文档名称、章节标题、页码、文档类型、业务部门、更新时间、权限标签等。
有了这些元数据,后期就能做出“先过滤、再检索”的精细化召回:比如用户只问某个产品线的内容,系统可以先筛掉其他产品线的片段再检索;用户权限不够的文档,在源头上就不会被召回。元数据还能支持后续的引用溯源——告诉用户“这段回答来自《技术规范》3.2节”,这对企业场景几乎是刚需。我强烈建议在建库阶段就设计好一套元数据结构,宁可先多存几个字段,也不要后期再补,因为大规模补元数据的成本非常高。
3. 检索:从知识库里“捞对”内容是一门手艺
3.1 向量检索的原理与参数细节
检索阶段的核心是计算用户问题与库中切片向量的相似度。相似度计算常见的有三种:余弦相似度(Cosine Similarity),衡量方向是否一致,对向量长度不敏感,是文本检索最常用的方式;内积(Dot Product),同时考虑方向和长度,要求索引库在使用前做好向量归一化;欧氏距离(L2 Distance),衡量空间中的直线距离,数值越小越相似。工程上,绝大多数文本向量库默认采用余弦相似度,因为它对语义匹配最稳定。
参数方面,每次检索都需要指定Top K——返回多少个最相似的片段。K值怎么选?太小容易遗漏关键信息,太大又会让模型“淹没”在无关上下文里。我的经验值是:通用问答场景,先召回5~10个片段;复杂分析场景,可以考虑把K值临时调大,但在重排序阶段再压缩。此外,很多向量库支持在检索时设置相似度阈值,低于阈值的片段直接丢弃,这能防止“矮子里面拔将军”——用户问的问题库里的确没有答案时,盲目把最相似的片段拿出来给模型,模型会基于这些片段强行编造。
3.2 关键词检索与混合检索:为什么不能只靠向量
向量检索好归好,但检索词命中问题一直是它的短板:如果用户问的是“价格”,而文档里写的是“费用”,向量检索可能找不到;但如果用户问的是具体编号、型号“ABC-123”,向量检索又会因为对稀有token不敏感而表现不佳。这个问题要靠关键词检索来补。经典的BM25算法至今仍然很能打,它基于词频和逆文档频率计算文本和查询的匹配度,在包含精确术语、编号、代码名等场景下,效果经常吊打纯向量检索。
把BM25和向量检索的结果混合起来,就是目前生产级RAG的标准操作。常见的混合策略有两种:加权融合和RRF(Reciprocal Rank Fusion)。加权融合是给两个检索结果分别打分,按权重合并,权重需要调参;RRF是每个结果按排名的倒数计分,把排名前若干位的结果汇总,鲁棒性更好,不需要额外调权重,我在项目中基本都采用RRF。混合检索的收益非常直观:在我测试的中文技术文档集上,单一向量检索的召回准确率约78%,混合后能到90%以上。
3.3 重排序:检索的“最后一道筛子”
如果混合检索是“海选”,那么**重排序(Rerank)**就是“终面”。向量检索阶段为了速度,本质上是用一个双塔模型做粗粒度匹配,这会导致一些语义上相关但表达差异较大的候选片段被排在后面。重排序阶段则不同,它用交叉编码器(Cross-Encoder)把“问题+片段”拼成一个整体输入模型,让模型输出相关性分数。因为交互更深入,重排序的相关性判断质量明显高于向量检索。
工程上,重排序通常针对我们前面混合检索召回的前20~50个片段进行,重排序后只保留前3~5个交给生成阶段。这样既控制了重排序的计算成本,又保证了最终上下文的质量。开源方案里bge-reranker系列是中文场景性价比很高的选择。需要提醒的是,重排序模型的推理速度比向量检索慢一个数量级,千万别把全库都拿去做重排序,只对候选集做,每秒处理几十个样本完全可接受。在Agent场景中,重排序还能用于多轮对话的场景——把之前的对话历史也拼进重排序的输入中,提升对“它”“这个”这类指代问题的处理效果。
3.4 检索优化的进阶手段:Query改写与HyDE
除了在库里下功夫,还能对“问题”本身做优化。用户提问往往是非结构化、口语化的,直接拿原始问题去做向量检索效果有限。我试过几个有效的手段。第一个是Query改写:让一个轻量大模型把用户的口语化问题改写成适合检索的规范表达,比如把“报销流程是啥来着”改写成“公司的报销流程是什么,包含哪些步骤”。改写后检索召回的准确率会有可感知的提升。第二个是HyDE(Hypothetical Document Embeddings):让大模型先根据问题生成一段“假想的理想答案”,再用这段答案的向量去检索。思路很巧妙——既然问题和文档之间的表达差异导致匹配偏差,那就把问题翻译成“更像文档的语言”,然后再去匹配。在某些垂直领域上效果显著,但生成过程会带来额外延迟和成本,需要权衡。第三个是多路召回与融合:并行执行向量检索、关键词检索、按元数据过滤的子检索,汇总后再重排序。多路召回能降低对单一检索方式的依赖,是生产系统稳定性的关键设计。
4. 生成:让大模型基于材料“好好答题”
4.1 上下文组装:提示词的结构决定回答的下限
检索到的片段再好,如果组装到提示词里时结构混乱,模型照样答不好。Prompt结构上,我推荐一个比较稳定的模式:系统指令明确模型身份和任务边界(你是知识库问答助手,只能基于提供的内容回答,不允许编造);提供检索到的参考资料,分条编号并标注来源;明确回答的约束条件(严格基于资料,不得使用资料外信息);最后给出用户问题。这种“任务指令-资料-约束-问题”的结构,比简单拼接“请根据如下资料回答问题:……”要好得多。
这里有一个化学上的“比例感”:上下文窗口有限,检索到的片段不能全塞进去。我之前实测,当参考资料总量在1500~2000个token时,模型的回答准确率和遵循度表现最好,超过3000个token之后,模型开始“迷失在中间”,开头和结尾的内容被重点关注,中间内容容易被忽略。所以给模型前要做一次上下文裁剪:优先保留重排序得分最高的片段,同时注意不要让重复信息占据过多空间。
4.2 幻觉抑制:三个关键约束
RAG最大的卖点就是能减少幻觉,但它不能完全消除幻觉。原因在于,即便有参考资料,大模型在生成时依然可能存在“自由发挥”的倾向。我在实践中总结出三个有效的约束手段。第一是指令级约束:在提示词里明确写“如果参考资料中没有答案,直接回答‘我无法从提供的内容中找到相关信息’,不要尝试猜测”。这个简单指令能大幅减少模型硬凑答案的行为。第二是引用级约束:要求模型回答时必须标注引用来源编号,格式如“根据[1][3]材料……”。当一个模型被要求给出处时,它的生成行为会天然变得谨慎,这是一个很实用的心理学技巧。第三是结构化兜底:设置后置校验规则,比如检查回答是否提到了引用,检查回答的实体是否出现在检索片段中,如果关键实体不匹配就进行告警或二次生成。这相当于在生成之后再加一道“质检闸门”。
4.3 检索结果不足时的“诚实策略”
还有一种情况经常发生:检索出来的片段确实和问题相关,但信息不完整,不足以支撑完整回答。这种时候,很多RAG系统会直接让模型用那一点残缺信息硬答,结果自然是片面的、甚至是误导的。我的处理方式是引入信息充分度判断:生成阶段前先让一个分类器(可以用大模型做)判断检索到的内容是否足以回答问题,判据可以包括关键词覆盖度、片段数量、内容与问题的语义相关度等。如果判断为“不足”,系统走第二条路径——返回“需要更多信息”的提示,同时把已检索到的相关片段作为“线索”展示给用户,或者触发Agent进入新一轮检索(这也正是Agentic RAG的入口)。
诚实策略看着是“退步”,其实对用户体验的伤害远小于给出一个看似正确实则误导的答案。我做过一个简单的AB对比:给“信息不足但强答”的答案标注为低质量,用户反馈中信任度明显下降;而“坦诚说不知道并给出线索”的路径,用户虽然没有得到完整答案,反而对系统整体评价更高。做RAG产品,这一点要想通。
4.4 流式输出与产品化细节
生产环境的RAG除了正确性,还要考虑体感。一个冷知识:RAG的响应链路比单纯的LLM生成更长,因为中间多了检索环节,所以耗时通常多出数百毫秒到数秒不等。这时候如果不做流式输出,用户面对的就是一个长时间转圈的页面,体验会很差。实现流式输出时,要设计好“检索动画提示”环节——先告诉用户“正在从知识库检索相关内容”,检索完成后再进入“正在生成回答”的流式阶段。这个细节能让用户感知到系统在做事,而不是卡住了。
流式输出的技术实现上,常见的是用SSE(Server-Sent Events)或者WebSocket把Token逐批推给前端。工程上要注意:检索阶段和生成阶段的衔接要流畅,不要在检索完成后再额外等待一个固定延时;建议把检索耗时和生成耗时分别记录,方便后续做性能监控。另外,如果系统支持引用标注,流式输出时还要同步把引用标记推给前端,让回答边生成边显示来源,可信度瞬间不一样。
5. Agentic RAG:当检索成为Agent的一个“行动”
5.1 从单轮到多轮:让Agent自己决定怎么查
传统RAG可以看作单轮闭环:问题进、答案出。但真实场景中,用户的一个复杂问题往往需要多步检索才能回答。比如用户问“我们公司上一季度各产品线的销售情况怎么样,重点分析下降最多的那条产品线”,第一步需要查到结构化数据里有哪些产品线,第二步需要对销售数据做聚合,第三步需要找到下降最多产品线的历史背景资料,这不是一次向量检索能搞定的。Agentic RAG就是让Agent把问题拆解成多步,逐步决定调哪个检索工具、用哪个查询词、是否需要看检索结果后再进行下一步检索。整体呈现出的行为模式是:检索 -> 判断信息是否够 -> 继续检索或开始生成。
实现Agentic RAG,通常让大模型具备“工具调用”的能力。可选用的框架很多,OpenAI的函数调用、Claude的工具使用,或者各类Agent框架(比如LangChain/LlamaIndex的Agent模式、开源的可视化Agent编排平台)。框架选型上,我建议优先选生态成熟、文档齐全的,不要一上来自己手写Agent循环,因为涉及工具schema定义、多轮记忆管理、异常处理等大量边界情况,很消耗时间。
5.2 工具规划与路由:检索也分“专线”
Agentic RAG的一个重要基础是多个检索工具的路由。与其把所有文档都扔进一个库里做通用检索,不如按业务域拆成多个知识库,每个库对应一个检索工具,让Agent根据问题意图自动路由。比如一个企业知识库系统,可以拆成“制度规范库”“产品技术库”“项目文档库”,Agent先判断用户问的是哪一类,再调用对应的工具去检索。这样做的好处是:每个库的数据量更小,检索噪声更少;不同库可以用不同的切片策略和嵌入模型;结果的可解释性也更清晰——知道答案来自哪个专项库。
工具路由的落地方式上,可以用一个轻量分类模型做意图识别,也可以让Agent自己根据工具描述选择。我实测下来,给工具写一段清晰的功能描述比单纯给工具命名更重要,大模型在函数调用时很大程度上依赖描述来决定用哪个工具。工具描述里要写明:“这个工具适合查询什么内容”“它包含什么范围的数据”“不适合解决什么问题”,大模型理解得更准确。
5.3 Agentic RAG与MCP的组合实践
再回到前面提到的MCP。在Agentic RAG架构中,知识检索工具完全可以封装为MCP服务,这样Agent与检索层之间就不再是直接硬编码的函数调用,而是通过标准协议进行服务发现和调用。这样做的好处是:知识库系统可以独立部署、独立升级;企业内部如果有多个团队维护了不同的知识库,Agent可以像“插拔U盘”一样接入或下线某个知识源;权限认证、调用审计等治理能力也能在协议层面统一做。
组合实践时的一个架构建议是:检索层做成MCP服务端,对外暴露“知识库查询”“文档详情获取”“知识库更新”等标准化工具;Agent侧通过MCP客户端发现工具、解析工具Schema,并把工具返回的数据转成后续推理的上下文。这样局部更新某个知识库的算法或模型时,完全不影响Agent主体,职责边界很清楚。
6. 多模态与GraphRAG:RAG的两个重要扩展方向
6.1 多模态检索:图文联合理解
纯文本RAG做久了,你会发现很多场景的需求不止文本。比如产品说明书里大量结构图、流程图,制度文件里的表格扫描件,培训资料里的PPT截图,这类信息如果用传统OCR抽文本,构图逻辑、数据关系会大量丢失。多模态RAG的思路,是把图片也用多模态嵌入模型转成向量,与文本向量一起入库,检索的时候同时匹配“文字相关”和“图像相关”的内容。
多模态检索的理想做法是用CLIP类的图文对齐模型,把图片和文本映射到同一向量空间。生成阶段,把检索到的图像本身作为多模态输入喂给带视觉能力的模型(如GPT-4o、Qwen-VL),让模型看图说话。这里有个工程细节要注意:纯文本查询与图片向量的匹配率天然偏低,建议做一层“文本-图像相关性重排序”的补偿,或者用大模型先根据图片生成文字描述,再把描述加入索引。不要指望一张复杂架构图能通过纯向量检索直接完美命中,多模态RAG目前最佳实践还是“图片+文字描述”双重索引。
6.2 GraphRAG:在知识结构上检索
还有一种近年特别受关注的扩展是GraphRAG。传统RAG各切片是独立存储的,检索时只能通过向量相似度“侧面”建立关联,缺乏对实体关系的直接建模。GraphRAG提前做实体识别和关系抽取,把文本内容里的“实体-关系-实体”三元组构建成知识图谱,检索时既可以靠向量检索命中某个片段,又能沿着图谱中的关系链把相关实体一网打尽。这类方案在处理“谁和谁相关”“某组织下有哪些分支”这类关联性问题上,效果要比纯向量RAG好一大截。
GraphRAG的工程代价不低——实体识别需要跑NLP模型,知识图谱的存储和查询需要图数据库(Neo4j、NebulaGraph等),建库流程明显变复杂。建议在核心业务问答场景用传统RAG即可,只有当问题高度依赖实体关联分析时再引入GraphRAG。这不是所有项目都需要的组件,属于“锦上添花”而不是“必需品”。
6.3 从“单一文档库”到“异构知识源”的架构演进
不管做多模态还是GraphRAG,最后都会落到“多知识源统一接入”这个架构问题上。成熟的RAG产品,一般都有这样的分层:接入层处理各种格式文档,解析层负责结构化,索引层按文档类型分表(文本表、图片表、图谱表),调度层根据查询类型自动路由到单一或组合知识源,生成层汇总各路召回结果统一生成。这种分层架构能让系统在面对新文档类型时只扩展接入层即可,不会动到核心检索逻辑。对于中小项目,先把文本这一路做扎实足够,多模态和GraphRAG按需增加即可。
7. 实战排查:RAG系统常见问题与调优速查
7.1 我踩过的六个典型坑
RAG系统出问题时,症状大多集中在“答非所问”“答案太浅”“检索不到相关内容”,但根源往往比表面复杂得多。我把实践中踩过的六个坑整理成速查表:
| 典型症状 | 根本原因 | 解决方向 |
|---|---|---|
| 相似问题回答质量波动大 | 切片策略不稳定,语义被切断 | 换语义边界切分,或父子切片策略 |
| 问专业术语搜不到 | 嵌入模型领域能力弱 | 换领域优化模型,或加关键词检索 |
| 答案全是废话模板 | 检索到的是低质量段落 | 清理文档噪音,加重量排序环节 |
| 数字和事实错误 | 切片内容被截断,关键上下文丢失 | 调大切片尺寸,加重叠区 |
| 检索速度慢 | 向量库无索引或数据量超限 | 检查索引配置,考虑升级向量库 |
| PDF里的表格答不对 | 解析层丢了表格结构 | 引入表格专用解析工具或OCR模型 |
7.2 调优顺序:先数据,再检索,最后模型
很多RAG项目在调试时容易陷入“动不动就换大模型”的误区。模型是RAG链路中最后一个被怀疑的对象,大概率也不是瓶颈源头。我的调优顺序是:先检查数据质量(文档有没有解析错、切片是否语义完整、元数据是否准确),再检查检索质量(召回率如何、Top K结果是否沾边、重排序是否把好结果排在前面),最后才动生成侧的模型参数和Prompt。数据问题不解决,换再强的模型也白搭。
检索质量好不好,可以用“召回率”指标来做量化诊断:取一批已知答案的问题集,看检索到的内容里是否包含足够支撑答案的关键信息。如果召回率不足80%,就不要先谈生成优化,先把切片和检索这一层打磨好。如果召回率已经不错但仍答不好,那就是生成侧Prompt或模型能力的问题。
7.3 评估闭环:让RAG持续“变聪明”
最后聊一个RAG项目能不能长期维护的分水岭——评估系统。如果没有一套可量化的评测数据集和指标,你根本无法判断这次优化到底有没有让系统变好。我建议项目起步时就建一个不少于100条测试题的评估集,每条测试题包含:标准问题、理想回答要点、必须出现的实体/事实、来源文档定位。每次改动(换切片策略、换嵌入模型、调Prompt)后都跑一遍评测集,对比准确率、召回率、“不知道”率、引用正确率等指标。
我自己的评估流程就是把评估集丢给系统批量跑,再用一个裁判模型对输出质量打分,分数作为回归基准。坚持两三个月以后,你会完整看到每次调整对整体效果的真实影响——哪些策略是“自我感觉良好但指标不动”的,哪些是“涨分明显但代价也可以接受”的。这种数据驱动的调优方式,比每次拍脑袋改一个参数然后靠感觉判断“好像变好了”要可靠得多。
我个人的体会是,RAG项目从“能跑”到“跑得好”之间,隔着的不是某个神秘组件,而是一层一层打磨出来的工程细节。建库时多想一步元数据设计,检索时多试一种混合策略,生成时多设一条“不知道就说不知道”的约束,都是在为最终效果积累胜势。希望这篇笔记能帮你在做Agent项目的路上少踩几个坑。后面如果有机会,我再单独整理一篇关于RAG离线评测和在线监控的具体实践。