RAG 评测指标怎么选
没有评测的 RAG 项目,改任何东西都是盲改:换切片策略、加重排、改提示词,做完之后只能靠"感觉好像好一点了"来判断。错觉一旦形成,会带着团队往错的方向走很久。
评测的目的不是打分,是定位:答案错了,要能立刻说出病在检索层还是生成层。
1. 先分层,再选指标
RAG 的答案质量由两段决定:有没有找到该找的内容(检索层),找到之后有没有照着说(生成层)。两层的指标完全不同,混在一起看就失去了定位能力。
| 层 | 要回答的问题 | 常用指标 |
|---|---|---|
| 检索层 | 该找的找全了吗?排得靠前吗? | Recall@K、MRR、nDCG@K |
| 生成层 | 说的是不是来自上下文?答的是不是这个问题? | Faithfulness、Answer Relevance |
一次改动如果只动了检索(比如加了混合检索),检索层指标应该动、生成层不该动。反过来,如果改了提示词之后检索层指标也变了,那多半是别的东西坏了。
2. 检索层:三个指标,三种用途
2.1 Recall@K:该找的找全了吗
Recall@K = 前 K 条里命中的相关切片数 / 全部相关切片数。
分子是"前 K 条里命中的条数",分母是"标注为相关的切片总数",不是"K"。
当每个问题只标了一个黄金切片时,分母恒为 1,这个指标就退化成命中率(命中记 1,没命中记 0)——此时它衡量的是"有没有找到",而不是"找全了没有"。要真正看"找全",标注时就要允许一个问题对应多条相关切片,否则 Recall@K 这个名字会给人虚假的安心。
它回答的是"有没有漏"。这是最该优先看的指标,因为漏掉的召回后面没有任何环节能补回来——重排只能在已有的候选里排序,生成层也看不到没召回的内容。
Recall@K 上不去,意味着切片有问题、索引没建全、或者查询改写没做。先修这个,再谈别的。
2.2 MRR:排得够靠前吗
正确答案第一次出现的位置取倒数,再对全部问题求平均。第 1 位记 1 分,第 2 位记 0.5,第 10 位记 0.1。
它回答的是"第一条就是对的吗"。这个指标和用户体验关系最直接——多数系统只把前几条送进上下文,所以第 1 位和第 5 位的差别,在实际产品里是"有答案"和"没答案"的差别。
Recall 高但 MRR 低,是典型的"找到了但排得靠后",这种时候加重排的收益最明显。
2.3 nDCG@K:整体排序好不好
考虑整个前 K 条的排序质量,越靠前的相关文档贡献越大。
它的用途是衡量重排效果。Recall 和 MRR 只看"有没有"和"第一个对不对",看不出第 2 到第 10 条的顺序是否合理;调重排模型时,要看的是 nDCG。
代价是标注成本高:需要给每个候选打相关性分数(而不仅仅是"对/错"),通常只在评测集比较小、需要精细调优时才用。
3. 生成层:两个问题分开看
3.1 Faithfulness:有没有编
答案里的每一句话,能不能在送进去的上下文里找到出处。
这是最重要的一条,因为它对应的是最坏的失败模式——编得像真的。有引用、语气确定、看起来很专业,但内容是模型自己补的。这类错误用户发现不了,发现的时候已经造成了后果。
测法是把答案拆成若干断言,逐条去上下文里比对。RAGAS(Es 等)的 faithfulness 指标就是这么做的:先抽断言,再逐条判定是否被上下文支持。
3.2 Answer Relevance:答的是不是这个问题
Faithfulness 高不代表答案有用。上下文里确实有这段话、答案也确实出自这段话,但用户问的是 A、答的是 B——指标上 faithfulness 满分,实际上完全没用。
所以两个指标必须一起看:faithfulness 低说明在编,answer relevance 低说明在答非所问,两者的修法完全不同。
3.3 用模型当裁判,但要防偏差
生成层的判定只能靠模型(LLM-as-Judge):把问题、上下文、答案一起给它,让它判断。这件事能做,但有三个已知偏差要防:
位置偏差。 裁判倾向于认为开头的内容更好。打乱候选顺序再判一次,看结论是否稳定。
长度偏差。 裁判倾向于给更长的答案打高分。如果改版之后答案变长了、分数也涨了,要先排除这个因素。
自我偏好。 裁判如果和生成模型是同一个,会给自己家的输出更高分。用不同的模型做裁判,或者定期抽样人工复核。
人工复核不是可选项:每隔一段时间抽几十条人工判一遍,看看机器分和人判的一致性。一致性下降,说明裁判该换了。一致性本身也要量化——两人标同一批样本算 Cohen's κ(一般要求 0.7 以上),或同一个人隔一周重标一批看稳定性。评测集自身的噪声,比任何指标算法的误差都更值得先解决。
4. RAGAS 的四个指标,各自对应哪一段
前面讲的指标是"该测什么",落地时通常不会自己实现,而是直接用一个框架。RAGAS(Es 等)是最常被拿来用的一个,它不止本文第 3 节提到的 faithfulness,而是四个指标,刚好覆盖两层(2026 年的 RAGAS 已扩展到 8 个指标,answer relevancy 也更名为 response relevancy;下面这四个是主干,先把它们理解透再看扩展):
| 指标 | 层 | 判的是什么 | 需要额外标注吗 |
|---|---|---|---|
| Context Precision | 检索层 | 送进上下文的切片里,有用的那些是不是排得靠前 | 视变体:无参考变体不需要标注 |
| Context Recall | 检索层 | 该找的内容有没有被找进上下文 | 需要,要标出答案所在的原文位置 |
| Faithfulness | 生成层 | 答案里的每一句断言,能否在上下文里找到出处 | 不需要 |
| Answer Relevancy | 生成层 | 答案是不是在回答这个问题 | 不需要 |
检索层那两个只看"送进上下文的内容",生成层那两个只看"答案与上下文、与问题的关系"——分工正好对应第 1 节那张表。
有两个容易搞混的地方要先说清:
Context Recall 不是 Recall@K。 前者量的是"标注里的相关句子有没有出现在检索到的上下文中",粒度是句子,而且它看的是最终进上下文的那几条;后者量的是"前 K 条里命中的相关切片比例",粒度是切片,发生在重排和截断之前。两者相关但不等价,别混着报数。
检索层的两个指标都要标注原文位置。 这也是第 5.2 节把"答案所在的原文位置"列为必标项的直接原因——不标就只剩生成层两个指标,出了问题定位不到段落。
四个指标单独看、组合看都有信息量,偏低时该动哪一段可以直接查这张表:
| 指标低 | 说明什么 | 先动哪一段 |
|---|---|---|
| Context Recall 低 | 该找的没进上下文 | 切片策略、混合检索的召回、候选取多少条 |
| Context Precision 低 | 进来的大部分没用 | 候选池过大、重排没做或没生效、过滤没前置到检索前 |
| Faithfulness 低 | 上下文是对的,模型在编 | 提示词约束、拒答规则、上下文是否过长 |
| Answer Relevancy 低 | 答非所问 | 查询理解与改写、提示词里对问题的复述、模型能力 |
两两组合更能定位:
- Context Recall 低 + Faithfulness 高 —— 典型的"没找到,但也没敢编",病在检索层,去修切片和召回。
- Context Recall 高 + Faithfulness 低 —— "找到了但没照着说",病在生成层,去改提示词和约束。
- 两个都低 —— 先修检索。生成层在上下文不对的时候几乎没有改善空间。
5. 评测集怎么建
指标定了,评测集才是真正的门槛。
5.1 从真实问题里来,不要自己编
自己编的问题有个系统性偏差:编的人知道文档结构,会不自觉地用文档里的原词提问。真实用户不会——他们用的是自己的词,还常常问得不完整。
最好的来源是线上日志里真实失败的问题、客服记录里的真实提问、以及同事的非专业提问。
5.2 标什么
最少要标三样:问题、期望答案要点(不是完整答案,是"答案必须包含什么")、以及答案所在的原文位置。
第三条最花时间但最值钱:有了原文位置才能算检索层指标,否则只能测生成层,出了问题定位不到段落。
5.3 规模与维护
50 到 200 条足够起步。太少则噪声大(改一两个 case 就能让指标跳几个点),太多则维护不动。
但"起步规模"和"能不能看出差异"是两回事,这一点几乎所有教程都不讲:100 条样本、90% 通过率的 95% 置信区间大约是 ±6 个百分点——两个版本差 2 到 3 个点,在这个样本量下根本分不清是改动生效还是抽样噪声。所以设阈值之前先做一次显著性判定:同一批样本上新旧两版配对比较(McNemar 检验或配对 bootstrap),差异不显著就不要拦。否则门禁会退化成"谁跑得早谁赢",最后大家学会绕过它。
评测集不是建完就放着:语料会变、产品会变、用户问法会变。文档更新之后,原来标注的原文位置可能失效,要定期复核。常见做法是在每次语料大版本更新后跑一遍全量,把失效的标注挑出来重标。
6. 门禁:让评测真的起作用
评测挂在 CI 里才有意义——每次改提示词、改切片、换模型,自动跑一遍,分数掉了就拦住。
设阈值时有两条经验:
按指标分层设。 检索层(Recall@K)和生成层(faithfulness)各设各的线,混成一个总分会掩盖问题。
用相对变化而不是绝对值。 "faithfulness 从 0.91 掉到 0.86"比"faithfulness < 0.9"更有操作性——绝对值会随裁判模型、评测集变化漂移,相对变化反映的是这次改动本身的影响。
另外,线上还要有一套独立的信号:用户点了"没帮助"、转人工、或者对同一问题反复追问,这些都是真实的负反馈。把它们回流进评测集,评测集才会越用越准——这件事在《RAG 链路与失败模式》里归在离线侧质量那一段,实际做起来是同一套数据闭环。