Keyboard shortcuts

Press ← or → to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

记忆怎么测——从「被注入」到「被采信」

这是我另一本小册《自顶向下拆 RAG》和这本之间欠了很久的一座桥:那本讲检索系统本身的评测,界面第 21 篇讲记忆的产品形态,但 agent 的长期记忆比传统 RAG 多出两层——宿主决定注入哪几条、模型决定真的去读哪几条。这一篇讲这两层怎么测,以及为什么「被注入」根本不是终点。

一、开场:同一个金标,在 agent 身上多了两环

传统 RAG 评测的链条很短:检索到、生成对,判分结束。我在 RAG 书里建立的整套纪律——holdout 封存、gold 标注、按位置计的召回指标——在 agent 记忆场景里仍然必要,但远远不够。

因为 agent 和检索框之间隔着两个自主决策:

  1. 检索回来 8 条候选,宿主决定把哪几条注入这一轮的上下文;
  2. 注入了 3 条,模型决定打开哪一条、信不信它、最终答不答对。

M 项目(我持续在看的那个单人维护开源 agent 内核项目,评测第 8 篇首次出场)在记忆面上做了两个月付费实验,四个决策面最后只活下来一个,还把一个离线 p=0.0005 的方案在端到端判了死刑。这一篇借它的病例立框架,框架本身从我的 RAG 书和评测系列长出来。

二、三层乘法链:写入 × 检索 × 采信

评测第 5 篇的乘法模型(检出率 = 读到 × 愿报 × 挡路)在记忆域原样重演。记忆系统是一条三层乘法链,任何一层断裂,下游失败都不能归因给上游:

层问题典型指标
写入该记的事实沉淀了吗?新旧记忆的关系判对了吗(同义/矛盾/补充)?覆盖率、关系判定准确率、误写率
检索该用的时候,金标在第几名?gold-at-1、gold-in-top-3、MRR
采信模型真的打开、核实并据此答对了吗?打开率、金标核实率、端到端答对率

归因折返规则也和检出率模型同构:端到端没答对,先看模型有没有打开注入的记忆(采信层断);打开了但没核实到金标,看金标在不在注入集合里(检索层断);金标根本没进库,看写入层。不逐层分开记账,「记忆系统没用」就是一句无法证伪的抱怨。

三、两个题库,两种金标,必须分报

M 项目用的外部题库是 LongMemEval 一类的长期记忆 benchmark(公开学术基准,成书前复核具体版本口径),但它内部把记忆库拆成两种形态,这个拆法值得照搬:

  • turn 级原子记忆库:每条记忆是一次对话里的一个原子事实(「张三的航班是周三」),金标是精确的一条;
  • whole-session 会话库:记忆是整段会话,金标可能散在好几段里,判分要看 top-3 而不是 at-1。

同一个方案在两个库上的成绩可以差出十个百分点(M 项目的迭代表里,弱判官方案在原子库命中 0.730、整段库只有 0.700,而基线在整段库有 0.725)。把两个库的数字平均成一个「记忆准确率」,等于把两种任务的失败互相抵消着藏起来。 这就是评测系列里「聚合指标是新形态遮羞布」的记忆域版本——按切片分层看,不许只报聚合。

金标纪律没有新东西:dev 集调参、holdout 在读题面之前冻结只报聚合统计,校准集和验证集分开(评测第 7 篇、RAG 书同此口径)。记忆题库唯一额外的要求是写入侧也要有金标:给定一段对话,「应该沉淀出哪几条事实」需要人工标注,否则写入层永远是一笔糊涂账。

四、召回与精排必须分家

这是两个月迭代里最贵的一课,先看伤亡数字。他们的第一版方案让一个 4B 判官独自决定「有没有相关记忆 + 注入哪几条」,结果 turn 级命中从基线 0.620 掉到 0.495(p=0.001),整段库从 0.720 掉到 0.450——加了智能,显著退步。

死因很清楚:判官读的是每条记忆 480 字节的聚焦窗口,看不到全文;而「有没有」这个判断需要全局视野。判官把大量「措辞迂回但确实相关」的记忆整片枪毙了。它擅长的是在几条候选之间比较「哪条更贴」,不擅长回答「这堆东西里到底有没有答案」。

定稿方案把两个判断分给两个机制:

  1. 词法检索(BM25)当地板,判「缺席」:top 分低于阈值时,认定答案不在库里,不注入也不咨询判官。召回是全文视野的活,交给读全文的词法信号。
  2. 判官只在「带」内排序:候选分数达到 top 一半(band)才允许判官参与,融合分 = 判官相关概率 + 0.5 × 归一化 BM25 分。弱语义信号和词法信号互补,谁也不许单飞。

band 有个漂亮的自适应性质:程序性记忆的分数分布很陡(第一名远超其余),band 一收,判官可挑的范围自动缩没,退化回纯基线——这防住了「判官自信地选中一条词法分只有第一名九分之一的兄弟任务 diff,然后模型照抄错文件」的真实事故;而事实型记忆分数平,band 覆盖全部候选,判官照常发挥。一个约束,两种数据形态自动适配。

我从这一课带走的通则超出记忆域:「在不在」和「是哪个」永远是两个机制的活。 触发评测里「该触发吗」和「触发后选哪个 skill」也是两道题(评测第 2 篇的双向口径);让一个看局部信息的弱判断者同时回答两个问题,它会在需要全局视野的那道上系统性出错。

五、shadow 的字节级同一性

记忆实验有个其他实验少有的便利条件:记忆干预通常可以在「宿主内部」完成,不改 provider 可见的字节。这给因果归因提供了一块硬地基——shadow 模式。

  • shadow:判官照咨询、判断照记账,但注入结果与不开功能时逐字节相同,模型什么都不知道;
  • advisory:判断才真正生效(行序置换、注入筛选);
  • 判官故障、超时、返回「都行」时,输出必须保持原始顺序,不许有半生效状态。

shadow 不是「先观察观察」的客气说法,它要过一个硬测试:同一输入跑两遍(shadow 开 / 关),diff 必须为空。 这和评测第 3 篇的「在场与送达证明」是同一种纪律——功能宣称自己没介入,就要拿出逐字节的证据,而不是「应该没影响吧」。

对照组侧的配套动作评测第 8 篇讲过:实验环境默认导出「判官关闭」,需要的臂再显式换回端点。记忆系统是默认值污染的重灾区——记忆功能一旦成为产品默认,对照组不做显式清除就必然被污染。

六、写路径:先造题,再开功能

检索面热闹了两个月,写路径(判官判断新记忆与旧记忆同义还是矛盾)在整个试点期一次都没被触发;另一个决策面(判断用户是不是在要求多方案枚举)咨询了 55 次,0 次越过 80% 的启用阈值。

这两个功能因此都处于一个尴尬状态:不是被证伪,是未测。「未测」和「证伪」必须严格区分——证伪可以下线,未测只能挂着,而挂着的功能不许进默认配置。

他们文档里写下的后续路线对所有做触发型功能的人都适用:先造评测,再决定开不开。 写路径需要的 fixture 要专门构造:同义改写(「我周三走」→「我的航班改到周三了」)、矛盾更新(旧事实被新事实推翻)、枚举请求(明确要求多列几个方案 vs 只是随口一问)。造不出能稳定触发的题,就没有该功能的确认性实验——这与评测第 2 篇「评估器为已发现的错误而建」互为镜像:触发型功能的合法出生证明是一份能触发它的题集。

七、最重的病例:注释有害,重排也没用

这一节把三层乘法链的最上层「采信」讲透,因为它是记忆评测最容易自欺的地方,病例分两幕。

第一幕:给模型看的建议,抵消了选择的收益。 早期方案会在每条检索结果后面附加相关度百分比、证据充分性评分和使用建议——把判官的判断翻译成给模型看的文字。60 例付费归因实验的结果:纯词法 33/60 核实到金标;只开静默注入筛选的臂 42/60;四面全开、带着注释的臂反而退回 34/60。注释把注入选择的增益整个抵消了。

这不是记忆面的孤立事故。同项目的停滞熔断观察到 76% 的进度提醒被模型无视;测试完整性机制发现模型削弱测试后发消息要求恢复,2 个 run 里 0 个服从。三个独立实验指向同一条规律:在长上下文、弱模型的 regime 下,文本型劝告是系统性失效的干预面。 这也解释了我自己在截断矩阵里的发现——「检出不难,告知才是缺口」(评测第 4 篇):告知缺口的存在,不等于「往输出里多塞几句告知」能填上它。

第二幕:换成静默重排,离线封神,端到端死刑。 注释方案死后,新方案不再输出任何文字,只在 BM25 band 内对结果行序做置换——advised 的结果和 plain 结果字节级一致,只是顺序变了。离线 holdout 极其漂亮:金标排第一 258→272/288,15:1,p=0.0005。

然后是评测第 9 篇详细讲过的端到端 null:139 行中 88 行因旧校验器判无效;放宽校验的探索性重评里金标核实 53→56(p=0.72)、答对 68→67(p=1.0)。整个决策面退役,分支 hash 保留供复现,名字留着但跳过并告警。

把两幕合起来,记忆评测的终极教训是:「被注入」不是终点,「排第一」也不是,终点是模型打开它、核实它、答对题。 中间指标越靠近机制本身越容易显著,越靠近用户价值越诚实——而层与层之间的断裂点(模型不按顺序读、建议文本被无视)只有端到端实验看得见。评测第 9 篇的代理链消费假设,就是从这个病例里抽象出来的。

八、记忆实验特有的污染清单

通用配对纪律(评测第 9 篇)之外,记忆实验有几张自己的脏牌:

  1. 跨被试记忆库泄漏:上一个任务写入的事实被下一个任务检索到。每被试、每任务全新存储,是记忆隔离的底线,比工作区隔离更重要——文件残留还能看见,记忆残留会伪装成「模型真聪明」。
  2. 对照组的默认 advisor:产品默认开启的记忆功能会在对照组里自动生效,详见评测第 8 篇,不赘述。
  3. 本地服务串扰:记忆服务按固定端口启动时,两个实验实例可能蹲到同一个端口、连上拒绝自己密钥的服务。M 项目出过真实事故(一个实例的任务因此卡了两天),修复是按状态根哈希分配端口、401 应答绝不认作自己的服务。测试环境里的「基础设施偶发失败」,有一部分是邻居实验。
  4. 判官端点的环境污染:转发判官请求的代码若读取系统代理设置,「判官不可达」会被染成代理的 503,还会测出一条产品根本不走的网络路径——对照组污染的网络版。

九、记忆是第一块能被严格测量的长期状态

收口说回为什么这件事值得做。agent 身上的长期状态正在快速增多:规则文件、托管记忆、技能沉淀、用户画像、任务历史。它们大多数现在都没法测——界面第 21 篇抱怨过「生效配置不可见」是用户侧的黑箱,而评测侧的对应物是「注入集合必须可记录、可回放、可判分」。

记忆是这堆长期状态里第一个拥有干净金标(事实可精确匹配)、天然配对形态(同一道题有记忆 vs 无记忆)、和清晰三层链的东西。它的评测法立住了,规则、画像、技能的评测才有模板可抄。也正因如此,这个战场上长出的纪律——召回精排分家、shadow 同一性、写路径先造题、采信才是终点、文本干预对弱模型失效——会比记忆系统本身活得更久。

本章外部病例来自 M 项目的记忆系统设计文档、排序方案退役相关 PR 与记忆试点合同(观察窗口 2026-10;项目名从略,原文链接与文档路径登记在写作简报),迭代数字(0.620/0.495/0.790、33/34/42 of 60、15:1、55 次咨询 0 越阈等)成书前由我凭链接复核;LongMemEval 为公开学术基准,引用时需核对所用版本与指标定义。自家框架出自《自顶向下拆 RAG》与评测系列(2026-08~10)。