# 六家记忆系统横评 · 100 题中英双查(bench6 v1.0) > **题集(已公开)**:`data/benchmarks/bench6-100-zh-en/`(`manifest.json` / `pool.jsonl` / `questions.jsonl`,CC BY-NC 4.0) > **六家结果(机器可读)**:`data/benchmarks/bench6-100-zh-en/results_v1.0.json` > 评分器:`md_cg/eval_common.py`(`unlock_global_cap()` + `use_jaccard()`),六家**同一套** hit@1 / hit@5 / MRR。 ## 一句话结论 在这份**零干扰、全为 gold 证据**的题池上:**中文查询**由灵枢词法(99.0%)与 Letta 归档直插(96.0%)领跑,**英文查询**则由 Letta 归档直插(73.0%)与纯向量 RAG(71.0%)领跑;灵枢四路融合在本池中**反而低于其单词法基线**(81.0% < 99.0%),条件桶/实体路在饱和池上稀释了词法命中。**Letta 的 agent 自主入库在本次口径下命中率为 0,根因不是检索失效,而是入库时把 `[turn_id]` 标记改写成自然语言、导致结果无法回溯**。 --- ## 1 口径与复现 | 项 | 取值 | |---|---| | 题源 | `data/benchmarks/locomo-zh-500/questions500.jsonl`(500 题,公开)+ 上游 LoCoMo 英文原问句(`mteb/LoCoMo`,revision `02e2c3dea15d9fdfd1cd7a0f65f5f8ae2ed4c1ac`) | | 语料 | `data/benchmarks/locomo-zh-500/corpus567.jsonl`(567 turn) | | 抽样 | qtype 分层 · 最大余额法 · `seed=7007` · n=100;配额 `single_hop 43 / adversarial 23 / temporal 16 / multi_hop 14 / open_domain 4` → 实际一致 | | 池 | 抽中 100 题的 gold 引用 turn 去重 = **137 条**;悬空引用 **0 条**(`dangling=[]`,已逐条记录规则) | | 写入文本(六家逐字同源) | `[] <英文原始陈述> [<会话时间>]` | | 中英双查 | 同 qid 两套词面:`question_zh`=中文关键词串、`question_en`=英文自然问句;`evidence_turns` 已断言逐字一致 | | 评分 | `first_evidence_rank`(1-based,未命中 0)→ `hit@1 / hit@5 / MRR`;统一前置开关 `unlock_global_cap()`(解除 LIKE 预筛 500 条截断)+ `use_jaccard()`(长 turn 不挤掉证据) | **验证(纪律 5,回放/断言全绿)**:题数=100、池=137、池内 id 唯一、每题中英问句均非空、中英 `evidence_turns` 逐字一致、竞品 `unmapped_rate=0`(除 Letta agent)、各臂 `errors=0`。 --- ## 2 主表:六家 × 中英 × 三指标 | 系统 | zh hit@1 | zh hit@5 | zh MRR | en hit@1 | en hit@5 | en MRR | 未回收率(zh/en) | |---|---|---|---|---|---|---|---| | 灵枢·单词法 | **99.0%** | 100.0% | 0.9950 | 47.0% | 69.0% | 0.5637 | n/a | | 灵枢·四路(真开bucket) | 81.0% | 100.0% | 0.8983 | 37.0% | 67.0% | 0.4893 | n/a | | 灵枢·四路(名义) | 68.0% | 100.0% | 0.8093 | 29.0% | 61.0% | 0.4212 | n/a | | 灵枢·词法+meta | **99.0%** | 100.0% | 0.9950 | 54.0% | 72.0% | 0.5993 | n/a | | 灵枢·四路(无meta) | **99.0%** | 100.0% | 0.9950 | 47.0% | 69.0% | 0.5637 | n/a | | 纯向量 RAG | 97.0% | 100.0% | 0.9817 | 71.0% | 91.0% | 0.7937 | n/a | | mem0 | 89.0% | 95.0% | 0.9125 | 68.0% | 93.0% | 0.7850 | 0.0% / 0.0% | | Graphiti | 58.0% | 63.0% | 0.6008 | 46.0% | 62.0% | 0.5303 | 0.0% / 0.0% | | GraphRAG | 31.0% | 35.0% | 0.3223 | 18.0% | 25.0% | 0.2057 | 0.0% / 0.0% | | Letta·归档直插 | 96.0% | 100.0% | 0.9767 | **73.0%** | 93.0% | 0.8063 | 0.0% / 0.0% | | Letta·agent自主 | 0.0% | 0.0% | 0.0000 | 0.0% | 0.0% | 0.0000 | **100% / 100%** | > 「灵枢」多行是**同一支系统在不同检索口径**下的对照,非多套系统;`灵枢·单词法 / 词法+meta / 四路(无meta)` 三者在中文侧同分(99.0%),差异只在英文侧(meta 使 en 47%→54%)。 --- ## 3 分题型附表(中文查询 hit@1,括号为题数) | 系统 | adversarial(23) | multi_hop(14) | open_domain(4) | single_hop(43) | temporal(16) | |---|---|---|---|---|---| | 灵枢·单词法 | 96% | 100% | 100% | 100% | 100% | | 灵枢·四路(真开bucket) | 83% | 86% | 100% | 77% | 81% | | 灵枢·四路(名义) | 70% | 79% | 75% | 65% | 62% | | 灵枢·词法+meta | 96% | 100% | 100% | 100% | 100% | | 灵枢·四路(无meta) | 96% | 100% | 100% | 100% | 100% | | 纯向量 RAG | 100% | 100% | 100% | 95% | 94% | | mem0 | 96% | 100% | 75% | 84% | 88% | | Graphiti | 48% | 79% | 50% | 56% | 62% | | GraphRAG | 52% | 29% | 25% | 26% | 19% | | Letta·归档直插 | 100% | 93% | 100% | 95% | 94% | | Letta·agent自主 | 0% | 0% | 0% | 0% | 0% | **读法**:灵枢系在 `multi_hop / open_domain / single_hop / temporal` 四项均为 100%,其唯一短板是 `adversarial`(96%,低 4pp);纯向量 RAG 与 Letta 归档直插则在 `adversarial` 与 `multi_hop` 上互补(前者 adversarial 100/后者 multi_hop 93)。GraphRAG 全题型垫底,`temporal_reasoning` 仅 19%(时间类问题依赖实体图上的时间边,而本臂以 `local_search` 的 sources 行序为准,未见时间维排序)。 --- ## 4 逐家入库形态与语言取证(本次最有价值的观测) 各家写入后**回读一条真实存储内容**,作为中英双查差异的解释变量: | 系统 | 存储形态(回读取证) | id 回收通道 | 取证 | |---|---|---|---| | 灵枢 | 中文四槽(身份/时间/摘要/条件)+ 英文原文,补 `tags`(裸词 identity+terms)与 `condition_space` | 图节点 id(进程内) | 库为自有 `MdCGOS`,`tags` 必须裸词(`ent:` 前缀在自然语言查询下永不命中) | | mem0 | 保留 `[turn_id] 英文原文`,另存 `metadata.turn_id` | `item["metadata"]["turn_id"]`(精确) | zh/en `unmapped=0` | | Graphiti | 一 turn 一 episode,抽取为实体/关系边 | `edge.episodes → EpisodicNode.name`(精确) | 137 episode 全部可回溯 | | GraphRAG | 文档级一次性索引,137 个 `text_unit`(原文切片) | `context_data["sources"].text` 正则(行序) | `index_rc=0`、`n_text_units=137`;**英文侧 7 题空 sources** | | Letta·归档直插 | `passages.create` 直插,**逐字保留** `[scene_0_session_11_turn_14] Caroline: …` | `passages.search().results[].content` 正则 | `search_field_path=['results']`;zh 96% / en 73% | | Letta·agent自主 | `messages.create`,agent 把内容**改写成自然语言摘要**(如 "Caroline is going through a transition…"),**不含 `[turn_id]` 标记** | 同上,但标记已丢 → 无可回收 | `search_field_path=['']`、`n_empty=100/100` | **结论**:Letta agent 模式的 0 分**不是检索能力问题**——`errors=0`、检索调用正常,而是**入库形态丢失了来源标记**,使任何以 id 回溯的评测口径都无法命中。评测「自主记忆」必须把「标记可追溯性」单列,否则会把可追溯性差异误读成检索能力差异。 --- ## 5 条件路由净效应(灵枢内部对照,中文查询) | 口径 | zh hit@1 | 相对单词法 | |---|---|---| | 单词法 | 99.0% | — | | 四路·真开 bucket(`context` 非空) | 81.0% | **−18.0pp** | | 四路·名义(`context=None`,bucket 路空转) | 68.0% | −31.0pp | **净效应为负**:真开 bucket 比名义口径**高 13.0pp**(说明条件桶路本身确实在工作、不是空转),但在本池中两者都低于单词法。归因见 §7 判定单 1——**零干扰池 + 短证据句**使词法已近饱和(99%),RRF 融合引入的并列项会挤占 Top-1。该结论**仅在本条件空间成立**,不可外推为「四路无用」。 --- ## 6 跨语言对照(中 → 英 的落差) | 系统 | 入库语言 | zh→en hit@1 变化 | |---|---|---| | 灵枢·单词法 | 中文层为主 + 英文原文 | 99.0% → 47.0%(−52.0pp) | | 纯向量 RAG | 英文原文直嵌入 | 97.0% → 71.0%(−26.0pp) | | mem0 | 英文原文 | 89.0% → 68.0%(−21.0pp) | | Letta·归档直插 | 英文原文 | 96.0% → 73.0%(−23.0pp) | | Graphiti | 英文原文 | 58.0% → 46.0%(−12.0pp) | | GraphRAG | 英文原文 | 31.0% → 18.0%(−13.0pp) | **读法**:入库语料与查询语料的**同源程度**决定跨语言落差。入库含中文层者(灵枢)中文查询登顶、英文查询垫底;入库为英文原文者(向量 RAG / mem0 / Letta)英文查询显著更稳。**没有一家在两种查询语言上同时最优**——这正是「中英双查」矩阵要暴露的事实。 **横向结论(不可忽略的第二层读法)**:把主表 11 臂逐行对比——**除全零壳臂 `letta_agent` 外,全部 10 臂的中文查询 hit@1 均高于英文查询,提升 +12 ~ +52pp**(灵枢·单词法 +52pp、词法+meta +45pp、纯向量 RAG +26pp、Letta·直插 +23pp、mem0 +21pp、GraphRAG +13pp、Graphiti +12pp)。也就是说,「英文查询更稳」只指**相对自身**的落差保持率(英文库 → 英文查询衰减更小);**绝对命中上,没有任何一家在英文词面下超过自己的中文词面**——查询词面敏感性(+12~+52pp)大于多数家间绝对差距。该结论可由公开脚本一键复现: ```bash python data/benchmarks/bench6-100-zh-en/run_bench.py ``` 脚本自带口径自证(用 `results_v1.0.json` 存档逐题 ranks 重算 summary 逐位比对)与 Adapter 接入协议(第三方记忆系统实现 `ingest`/`search` 即可同口径入评)。归因边界照旧:`question_zh` 为关键词串(保留英文专名/日期词)、`question_en` 为自然问句,中文提升混合语言与查询形态双因素;内置词面基线在纯英文库上呈反向 en>zh(`--demo`),恰证「查询语言优势取决于系统如何处理语料」。 --- ## 7 偏差归因(设计者视角判定单) ### 判定单 1 · 灵枢四路真开 bucket 反低于单词法 ``` 条件空间:观测位置=全局观测层(评测编排)|观测工具=eval_common 证据命中(unlock_global_cap+use_jaccard)|时间窗口=bench6 单次全量(seed=7007)|存在约束=池内每题 gold 仅 1–2 条、证据为高度可分词短句 白箱三问:依据=同池同题同口径下 四路 81% < 单词法 99%(且名义 68% < 真开 81%)|条件=仅当「池内零干扰 + 证据短句高度可分词」时成立(词法已饱和,条件桶/实体路引入的并列项挤占 Top-1)|错后=若池含干扰或证据变长,四路应回优 裁决:REJECT(「四路必然优于单词法」为假) 依据:同池下 hit@1 单调 单词法 99% > 真开 81% > 名义 68%;真开比名义高 13pp 证明 bucket 路在工作,非空转 缺失维度:条件边界(池干扰度) 验证路径:在 567 全池(含干扰)上复跑两口径,若四路反超则归因成立 关注信号:条件路由的价值应在「语义/条件类查询 + 有干扰池」中体现 ``` ### 判定单 2 · Letta agent 自主入库 0% ``` 条件空间:观测位置=全局(入库形态取证)|观测工具=passages.list 回读 + search field path 取证|时间窗口=全量 137 写入后|存在约束=agent 写入经 LLM 改写、core block 存自然语言摘要 白箱三问:依据=ingest_probe 内容为 "Caroline is going through a transition…",不含 [scene_*_turn_*] 标记|条件=凡入库经 LLM 重写且不保留原始标记者,id 口径必无法回溯|错后=该结论支持「自主入库丢失可追溯性」,写入 negative 裁决:REJECT(不是检索失败,而是入库形态丢失标记导致不可回收) 依据:errors=0、检索调用正常、field=['']、n_empty=100/100;对照 archival 直插(保留标记)96%/73% 正常 → 差异锁定在入库语义 缺失维度:存在约束(stored-form 是否保留 source id) 验证路径:对比 archival 直插(保留标记)96%/73% 正常 → 差异锁定在入库语义,不在检索 关注信号:评测「结构化/自主记忆」须区分「标记可追溯性」 ``` ### 判定单 3 · 灵枢词法 0.99 ≠ 公开参考 0.936 ``` 条件空间:观测位置=全局|观测工具=同一 eval_common 词法|时间窗口=不同池规模两次评测|存在约束=bench6 池=137(仅抽中题 gold,零干扰),公开池=567(全语料含干扰) 白箱三问:依据=manifest pool.n=137 vs 公开 n_pool=567;同算法随池缩小命中单调上升|条件=池内零干扰时指标为上界|错后=如池扩回 567 应回落至 ≈0.936 附近 裁决:DEFER(非矛盾,是「不同条件空间不可直接等同」) 依据:算法(first_evidence_rank + 同口径)未变,唯一改变的条件是池规模 缺失维度:条件边界(池干扰度/池规模) 验证路径:以 bench6 池跑公开配置、或以 567 池跑 bench6 配置做交叉验证 ``` ### 判定单 4 · 灵枢英文查询远低于中文 ``` 条件空间:观测位置=全局|观测工具=hit@1|时间窗口=同库双查|存在约束=灵枢库存中文层+英文原文,查询为中文关键词串 vs 英文自然问句 白箱三问:依据=灵枢 zh 99% / en 47%;纯向量 RAG zh 97% / en 71%|条件=词法路命中依赖查询词面与入库词面同语言|错后=若英文查询也能命中中文层(双语词项映射),en 应上升 裁决:ACCEPT(条件证据充分:入库语料与查询语料同源程度差异) 依据:跨语言矩阵——凡入库英文原文者英文查询均不低于灵枢;中文查询则灵枢居首 缺失维度:无 验证路径:给灵枢补「英文查询→中文层」跨语言词项映射后再测 ``` --- ## 8 观测:写入 / 查询成本(137 条池) | 系统 | 写入耗时 | 中文查询 100 题 | 英文查询 100 题 | |---|---|---|---| | mem0 | 177.7s | 6.4s | 6.7s | | Graphiti | 416.4s | 6.8s | 7.3s | | GraphRAG | 建索引 616s(一次性) | 346.2s | 182.1s | | Letta·归档直插 | 59.0s | 38.0s | 38.3s | | Letta·agent自主 | 418.7s | 58.3s | 58.8s | | 灵枢(**rust 引擎**)·单词法 | 进程内,未单列¹ | **0.008s** | **0.019s** | | 灵枢(**rust 引擎**)·四路 | 同上¹ | 0.012s | 0.023s | | 灵枢(**rust 引擎**)·词法+meta | 同上¹ | 0.009s | 0.021s | | 纯向量 RAG | 进程内,未单列 | — | — | > ¹ 灵枢写入走 python 进程内(`mdcg-eval` 为**只读检索核心**,无写入路径),未单列计时。 > **rust 三行为 rust 检索核心实测**(非 python):`mdcg-eval --serve` 引擎,预热 10 请求后逐请求 `perf_counter` 计时,口径 = 客户端端到端 JSON 行 IPC 调用 100 题的总墙钟时间(单题均值 0.07–0.24 ms,p95 ≤ 0.34 ms;复跑波动 <15%)。计时同批 hits 复算 hit@1/hit@5/MRR 与 py 基线逐项一致——测的即主表对齐口径。脚本与数据:`docs/experiments/bench6-rust-rerun/bench_latency.py` / `rust_latency.json`。竞品行含各自 SDK/HTTP 客户端开销,同为端到端口径,量级差距(10²–10⁴ 倍)远超客户端差异。 --- ## 9 诚实边界(报告须原样引用) 1. **池全为 gold 证据 → 池内零干扰,指标是上界**,不是端到端记忆能力;真实场景存在大量干扰 turn,各家差距可能与本表不同。 2. **`question_zh` 是中文关键词串而非自然语言问句 → 评检索命中,非 QA**;无答案文本,无法评答案质量。 3. **n=100 时题级命中率 CV≈8.3%**(n=500 时 3.7%,容量减半按 √5 放大)→ **家间差距小于约 16% 不可下结论**。据此,主表中「灵枢词法 99% vs 纯向量 97%」等差距**不可判为显著**;而「99% vs 0%(Letta agent)」「99% vs 31%(GraphRAG)」等大落差可下结论。 4. 竞品行序为各家**自身返回顺序**(mem0/Graphiti 按相似度或图序,GraphRAG 为 sources 行序),非统一重排——差异部分来自各家排序口径本身。 5. Letta 分「归档直插 / agent 自主」两模式分别报告;**不得**以 archival 的分数代表 Letta 整体,也不得以 agent 的 0 分否定 Letta 检索能力。 --- ## 10 复现命令 ```bash # 1) 固化口径层(首次;幂等)——题集已在 data/benchmarks/bench6-100-zh-en/ python -m md_cg.bench6_common --force # 2) 主进程臂(灵枢 5 口径 + 纯向量 RAG) python -m md_cg.bench6_arms # 3) 六家统一评分(主表 + 分题型 + 落盘) python -m md_cg.bench6_competitors --k 5 ``` **外部依赖(仅竞品臂需要)**:四家 LLM 竞品(mem0 / Graphiti / GraphRAG / Letta)的适配脚本运行在评测工作区,各以独立虚拟环境隔离,分别需要自身的图数据库服务、本地嵌入服务、记忆服务与 LLM API(其为各家服务的本地对接代码,涉各家凭据)。**公开评测入口不依赖任何竞品栈**——`data/benchmarks/bench6-100-zh-en/run_bench.py`(零依赖)提供口径层复现(默认运行即做口径自证)与 Adapter 协议(实现 `ingest` / `search` 两个方法即可接入任意系统跑同一题集),**接入任意 LLM 与向量方法进行测试都可复现**。本仓库公开的是**口径层 + 题集 + 评测入口 + 六家结果**,竞品数字可由 `data/benchmarks/bench6-100-zh-en/results_v1.0.json` 逐题核对。全流程按 AGENTS 第 15 条走 argv 列表 + `PYTHONUTF8=1`。 --- ## 11 数据来源与署名 - 中文派生题库/语料:`locomo-zh-500`(本项目派生并公开,源自 LoCoMo,**CC BY-NC 4.0**)。 - 本报告题集:`data/benchmarks/bench6-100-zh-en/`(100 题 / 137 池,**CC BY-NC 4.0**,沿用上游许可)。 - 英文原始问句/陈述:上游 LoCoMo(经 `mteb/LoCoMo` 获取,revision `02e2c3dea15d9fdfd1cd7a0f65f5f8ae2ed4c1ac`)。 - 竞品版本:mem0 / Graphiti / GraphRAG 3.1.2 / Letta(`letta_client` 1.12.1)。 - 评分器:本项目 `md_cg/eval_common.py`(六家同口径,未改动既有指标实现)。