M7 FPR 与 normalFalsePositiveRate
昨天 Day 161 把 4 个 outcome 指标的公式与数据源钉成了 metricsSpec。
阶段: B17 · outcome 指标仪表盘 + A/B(Day 161-170) 标签: #false-positive-rate #ground-truth #circular-eval #bootstrap-ci
今日导引(由浅入深)
昨天 Day 161 把 4 个 outcome 指标的公式与数据源钉成了 metricsSpec。
今天 Day 162 落地其中第一个、也是最容易自欺的那个——FPR(误报率)。
难点不在公式(公式 Day 161 已写死 fp/(fp+tn)),而在「真值从哪来」:现有 evalBaseline.ts 的 normalFalsePositiveRate 是用同一套规则既当预测又当裁判算出来的,必然偏乐观。今天要把它换成「预测与真值来源分离」的独立金标评测。
在 B1→B18 曲线上,这是「评测可信度」从合成自评升级到外部金标的关键一步。
最小可判定产出:调用 groundTruthEval.ts 的 binaryEvalWithCI 跑出一个 prediction-source-agnostic 的 FPR 基线数(合成 golden 集可先出占位数)。
1. 机理精读
循环自评(circular baseline)为什么必然乐观。
src/aml/evalBaseline.ts 的 evalRuleBaseline 对每个案件做 assessCase(c).topTypology ?? 'normal' 当预测,再拿 c.label 当真值算 normalFalsePositiveRate。
问题在于:合成数据集是同一作者按规则生成的,规则引擎又是按同一套规则判定的——预测器和真值生成器共享了同一套先验。
规则没覆盖到的边角恰恰也不会出现在合成数据里,于是误报「碰巧」很低。这不是 FPR,是规则对自己生成物的拟合度。
正确做法:prediction-source-agnostic。
src/aml/groundTruthEval.ts 的设计就是为修这个循环:它只接受 {label, predicted} 配对,两边都可以来自外部源——
- label 来自公开标注集(IBM AMLworld / Elliptic / PaySim);
- predicted 来自真实 LLM。
预测器和真值生成器彻底解耦,算出来的 FPR 才有外部效度。
模块头注释把这点写得很直白:「The circular weakness of evalBaseline.ts is that the SAME rule engine that predicts is graded against the SAME author's synthetic generator. This module is prediction-source-agnostic.」
为什么 FPR 还要带 bootstrap CI。
单点 FPR=0.18 不告诉你「这个 0.18 有多稳」。在 N 不大时,重采样波动可能让真实 FPR 落在很宽的区间里。
binaryEvalWithCI 做的就是对配对样本做 B 次有放回重采样(默认 2000 次),每次重算 FPR,排序后取 2.5/97.5 分位得 95% CI。
这与 B17 整体「小样本只示方向、不证显著」的纪律一脉相承——给 FPR 配 CI,就是诚实地告诉读者这个误报率的不确定性。
与相邻概念的边界。
今天只解决「FPR 真值从哪来、怎么算」,不解决「真实公开集已下载并跑出真数」——那是 network/data-gated 的外部动作。
当前能做的是:把 evalBaseline 的 FPR 口径切到 binaryEval,用合成 golden 集先跑出占位数,证明接线正确。真实 FPR 数要等公开集下载后才有。
2. 推导 / 手算 / 代码走读
groundTruthEval.ts 已 built + tested(纯函数 + 可注入 RNG 的确定性测试)。关键符号走读:
-
binaryEval(items, normalLabel='normal'):把多类型学折叠成「可疑(positive) vs normal」二分类。- 对每条
{label, predicted},actualPos = label !== normalLabel、predPos = predicted !== normalLabel,据此累加 tp/fp/tn/fn。 - FPR 行为:
fpr: fp + tn ? fp / (fp + tn) : 0——分母为 0(无 normal support)时返回 0,需查原始 fp/tn 字段区分「无样本」与「真为零」。
- 对每条
-
binaryEvalWithCI(items, opts):- 先算点估计
binaryEval; - 再做 B 次有放回重采样(
opts.bootstrap ?? 2000,非正整数会throw),对 recall/precision/fpr 各收集一个分布; - 排序后用
percentile(arr, 2.5)/percentile(arr, 97.5)取 95% CI; - RNG 可注入(
opts.rng)以保证测试确定性。
- 先算点估计
-
LabeledPrediction接口:{label, predicted}——刻意只要这两个字段,强制调用方把预测源和真值源分别接进来,结构上杜绝循环自评。 -
对比
evalBaseline.ts的normalFalsePositiveRate:- 后者在循环里
predicted = assessCase(c).topTypology ?? 'normal'; if (c.label === 'normal') { normalN++; if (predicted !== 'normal') normalFp++ };- 最后
normalN === 0 ? 0 : normalFp / normalN; - 数学上等价于
binaryEval限定在 normal 子集上的 FPR,但预测源被钉死成内部规则引擎——这正是要被替换掉的循环点。
- 后者在循环里
手算验证:
金标 [normal, normal, normal, structuring, layering],预测 [structuring, normal, normal, structuring, normal]。
逐条折叠:
- normal / structuring → fp
- normal / normal → tn
- normal / normal → tn
- structuring / structuring → tp
- layering / normal → fn
得 tp=1, fp=1, tn=2, fn=1。
- FPR =
fp/(fp+tn) = 1/3 ≈ 0.333 - recall =
tp/(tp+fn) = 1/2 = 0.5
这是确定性手算,可作单测断言。
3. 今日实战
- 把
src/aml/evalBaseline.ts的 FPR 口径改为读agent-evals/labels金标,不再用规则引擎自评。 - 调用
src/aml/groundTruthEval.ts的binaryEvalWithCI计算 FPR 基线(带 95% CI)。 - 在缺真实公开集时,用
src/aml/generator.ts的getGoldenDataset合成 golden 集先跑出占位 FPR 数,验证接线。 - 留好接入位:等公开集(AMLworld/Elliptic)下载后,把 label 源切到真实标注,predicted 源切到真实 LLM,跑出真 FPR。
4. 今日实测 / 产出
groundTruthEval.ts的binaryEval/binaryEvalWithCI已 built + tested。- 真实公开数据集(AMLworld/Elliptic)的 FPR/precision/recall = 待数据(下载公开集)。
- 落地后将产出形如 FPR=0.18 的金标基线数;当前用合成 golden 集(
generator.ts的getGoldenDataset)可先跑出占位数。 - 当前不产生真实外部金标 FPR——占位数仅证明接线正确。
5. 常见误区 / 陷阱
- 继续拿 evalBaseline 自评 FPR 当对外数字:循环自评的 FPR 不可对外宣称,只能当内部健全性检查。
- 把占位 FPR 当真值:合成 golden 集跑出的 FPR 是接线占位数,不是外部效度的误报率。
- 报点估计不报 CI:N 不大时单点 FPR 误导性强,必须带
binaryEvalWithCI的 95% CI。 - 分母为 0 误读:
fpr在无 normal 样本时返回 0,要查原始fp/tn区分「无样本」与「真为零」。
6. 学习资源(每条带 YYYY-MM)
- Anthropic「Demystifying evals」——「独立金标 vs 循环自评」核心论点(2026-01)。
- IBM AMLworld 合成 AML 数据集(2024-04)——公开 label 源候选,需复查是否有更新版。
- Elliptic / PaySim 公开 AML 标注集(持续维护;接入前复查最新版本)。
- 本仓代码:
src/aml/groundTruthEval.ts(prediction-source-agnostic 评测)、src/aml/evalBaseline.ts(待替换的循环自评)、src/aml/generator.ts的getGoldenDataset(合成占位源)。
SOTA检查 (2026-06 更新)
- 当前主流:「独立金标 vs 循环自评」是 Anthropic 2026-01 evals 指南的核心论点,仍 SOTA;bootstrap CI 仍是误差量化的标准做法。
- 过时黑名单:禁止再用
evalBaseline的自评 FPR 当对外数字。 - 下次复查点:复查 AMLworld(IBM 2024-04)是否有更新版本;该集已接近 24 个月口径,长文里需标注其历史性并补 2025-2026 公开集。AMLA 配套 RTS 对「FPR 可接受阈值」若有口径,需同步复查。
衔接
- 昨天:Day 161 — M7 outcome 指标定义(立 4 指标骨架与 metricsSpec)。
- 今天:把 FPR 从循环自评切到独立金标,用
binaryEvalWithCI算带 CI 的 FPR 基线(合成集先出占位数)。 - 明天:Day 163 — M7 SAR 质量量化(把 narrative 拆成可打分维度聚合成 0-1 分)。