
AgentMercury 这个思路真正值得关注的地方不是模型结构又有了什么变化而是它把训练和评测拆开了。这个“拆开”不是简单的数据划分而是“训练环境与评测集脱钩”训练阶段让智能体在它自己的环境里试错评测阶段却用一套和训练环境不同分布、不同情境、甚至不同交互规则的任务来考核。这样做的好处是评测结果能更接近真实未见过场景的表现而不是“背题”成绩。说得直白一点如果你是做智能体、对话系统或强化学习任务并且发现模型在评测集上分数越来越高但换一批任务就明显变笨那大概率不是模型能力不够而是训练环境和评测集绑得太紧。下面围绕这个现象拆一下 AgentMercury 的脱钩思路怎么落地以及怎么验证它确实提升了泛化能力。1. 别急着追模型结构先看“训练环境和评测集脱钩”这件事1.1 AgentMercury 真正解决的不是训练得更久而是测得更准AgentMercury 具体用什么网络结构、用什么强化学习算法这里不展开。因为它真正值得讨论的不是结构而是评测方式。这个判断要放在智能体训练的背景下看。智能体不像普通分类模型那样只吃固定输入它要在环境里去决策、去尝试、去拿反馈。训练结束后我们通常会用另一批任务来评估它的能力。这里的问题在于如果评测任务和训练任务来自同一个环境生成器甚至就是从训练数据里留出来的一部分那么智能体完全有可能通过记住环境特征、奖励模式、状态分布来拿高分而不是通过学会通用的决策能力。所以 AgentMercury 的核心价值不是“换一个更大的模型”而是“换一套更严格的考试方式”。考试题目如果和平时练的题相似考出来的分数再高也不能说明真实水平。这个道理放到智能体训练里就是训练环境与评测集脱钩的核心原因。1.2 脱钩不是把评测集藏起来而是切断“评测集来自训练环境”这条捷径脱钩会让人误解成“评测时换一批新数据”但这里远不止换数据。脱钩要求的是评测过程中不能依赖训练环境里才有的信息。我一般从两个层面理解数据层面评测任务的文本、图片、环境状态、工具调用链路不能是训练环境里已经出现过的数据也不能是同分布直接抽样出来的数据。接口层面评测时给模型提供的观测、动作空间、奖励信号不应沿用训练环境完全相同的编码方式。如果训练时靠某个隐藏状态拿到高分评测时这个状态不存在智能体还能不能正确决策这才是真正的考察点。换句话说脱钩是切断“评测集来自训练环境”这条捷径。评测集不是训练集随机的另一个子集而是独立设计的一套评估协议覆盖训练环境没见过的分布。这样一旦分数下降我们能更早发现真实的泛化短板而不是等到上线才暴露。2. 训练环境和评测集一旦“黏在一起”泛化能力会被虚高掩盖2.1 评测分数高不代表到了新环境还高常见做法是智能体在某个环境里训练然后从训练环境里随机抽任务做评测每轮还在调整超参。最终评测集分数一路涨看起来模型在进步。实际上评测任务和训练任务共享同一个状态分布、同一个奖励函数、同一套工具列表智能体并不需要学会非常泛化的策略只要在训练环境里找到规律就能赢。这种情况下模型学到的是“当前环境的快捷方式”不是“解决一类问题的能力”。换到另一套环境界面变了、状态编号变了、任务目标表达变了分数就会掉得很明显。所以评价一个智能体不能只看它在训练环境上的评测而要看它到独立评测集上的迁移表现。AgentMercury 的脱钩思路本质上是把“在训练环境里的表现”和“在陌生任务上的泛化能力”分成两件事看。2.2 常见泄漏路径状态信息、奖励信号、分布记忆我排过一次智能体评测问题发现分数虚高往往来自三条路径状态信息泄漏。智能体能看到的环境状态里藏了训练时容易识别的特征比如关卡编号、特殊 token、固定开头。评测集如果仍然包含这些特征模型不需要推理就能输出正确答案。奖励信号泄漏。训练时回报函数会在某一类行为后给高分。评测时如果不换奖励设定模型只要复现训练时的“肌肉记忆”就能拿高分而不是在新环境里探索。分布记忆。评测任务虽然没用训练数据但生成方式和训练环境一致比如同样一批模板只是换了几个词。模型见过大量类似模板后本质上是在做模板匹配。这三种泄漏其实很难用“数据不重叠”来消除。必须让评测环境在分布上、交互规则上、奖励设计上都和训练环境拉开距离。泄漏路径表现脱钩后影响状态信息泄漏模型看到固定编号就输出去掉固定编号后动作随机奖励信号泄漏训练中某些动作得分高换奖励设定后策略失效分布记忆换模板也能对换表达方式后错误率上升2.3 用 yolov5 训练环境搭建来理解“环境一致”的诱惑yolov5 这一类的视觉模型训练能很直接地解释这个问题。很多人第一次训练 yolov5 时会把同一批图片随机分成训练集和验证集。这里有个隐蔽问题同一段视频里的连续帧或者同一个设备在同一个场景下拍的照片很容易同时出现在训练集和验证集里。模型看过这些图片的相似特征验证集分数自然很高。但把模型部署到新的工厂、新的摄像头、新的光照条件下mAP 立刻下降。这种随机划分的问题就在于验证集和训练环境太一致。评测图片虽然文件不同但来源场景相同相当于“训练环境与评测集黏在一起”。要让泛化结果可信就要按场景、按设备、按时间段来划分验证集让验证集的核心分布与训练环境脱钩。这和 AgentMercury 的思路是相通的。3. 把脱钩落到实操从构建独立评测集到统一评测协议3.1 第一步把训练环境和评测环境拆成两套配置先做配置拆分。训练环境通常包含环境名称或 ID状态观测格式动作空间奖励函数任务模板列表最大步数评测环境不能继续使用这份配置。可以单独建一份 eval_config字段对应但内容不同。比如train_env: env_id: mercury_town_v1 observation: text action_space: navigate, talk, use_tool reward: task_complete step_penalty task_templates: [template_set_A, template_set_B] eval_env: env_id: mercury_town_eval_v2 observation: text structured_context action_space: navigate, talk, use_tool, ask_clarify reward: task_complete efficiency_score task_templates: [template_set_C, template_set_D, template_set_E]这里的关键是评测配置里不能只改 task_templates 一个字段。状态格式、奖励函数、工具范围最好也要有差异。如果完全一样评测集就变成了训练环境的一个版本号脱钩也就失去了意义。3.2 第二步让评测集覆盖“训练环境没见过”的分布构建评测集时不能只从训练分布抽样。要刻意加入训练环境覆盖不到的分布。拿对话评测集构建来说训练数据如果都是客服问答模板评测集就应该包含不同语言风格的输入不同领域的任务不同数量的工具调用混合了异常输入的情况需要澄清和追问的场景否则只能证明模型会做客服问答模板不能证明它具备对话能力。这里还要考虑评测集的难度和区分度。如果评测集太简单大家都能拿满分脱钩就没有意义。如果评测集太难模型完全做不出也难以判断是模型问题还是任务不合理。一般建议先把评测任务按难度分层然后观察模型在每一层的成功率。3.3 第三步设好评测协议避免人为偏差评测集独立还不够评测过程也要固定。我见过不少项目评测集没问题但评测协议不统一允许模型重试 3 次和只允许 1 次结果差别很大超时时间一个用 10 秒一个用 60 秒最终答案解析方式不一致同一个输出有时判定对有时判定错随机种子不固定状态初始化每次都不同所以评测协议至少要包含这些项每回合最大步数每一任务最大尝试次数超时时间随机种子答案解析规则成绩统计方式成功率、平均步数、平均分数这些参数要在评测开始前锁死并且写进配置里。评测结果如果只记录一个总分没有协议细节后续很难复现。3.4 一个最小化的评测执行伪代码给一个通用伪代码不是 AgentMercury 的源码但可以体现脱钩评测的流程def run_evaluation(agent, eval_cfg): results [] for task in eval_cfg[tasks]: env create_env(eval_cfg[env_config], seedeval_cfg[seed]) obs env.reset(task) done False steps 0 while not done and steps eval_cfg[max_steps]: action agent.act(obs) obs, reward, done, info env.step(action) steps 1 results.append({ task_id: task[id], success: info.get(success, False), steps: steps, score: info.get(score, 0), }) return summarize(results)注意这里 create_env 必须使用 eval_cfg[env_config]不能顺手传训练环境配置。如果两套环境封装在同一类里也要用不同的初始化参数。评测代码里不应该出现先加载训练环境再替换任务的写法这样很容易把训练环境的隐藏状态带进评测。4. 脱钩之后怎么判断泛化真的提升了4.1 四个可量化的观察指标脱钩不是口号要能验证。我建议至少盯四个指标同分布评测分数也就是训练环境内评测看模型有没有保住基本能力。脱钩评测分数独立评测集上的成功率或得分这是核心指标。分数差距同分布分数减去脱钩分数。这个差距越小说明模型不是在背题泛化越稳定。方差稳定性同一模型多次评测的波动。如果标准差很大说明结果受随机初始化或评测任务抽样影响太大不足以判断泛化。指标含义期望同分布评测训练环境内任务表现保持稳定即可脱钩评测独立任务表现越高越好分数差距同分布 - 脱钩越小越好多次评测方差稳定性越小越好不要只追求脱钩评测分数这一项。如果同分布分数很高、独立评测分数很低恰恰说明之前的评测体系掩盖了过拟合。4.2 判断标准评测分数下降不等于模型退化脱钩之后很多人的第一反应是分数怎么降了。这其实是正常的。比如某个智能体在同一分布下评测分数 92 分脱钩评测只有 74 分。很多人会觉得模型退化了于是又跑回原来的评测集调参直到分数回升。但这样做又回到了“绑定训练环境”的陷阱。正确做法是先看下降的分布。如果同分布 92 分、脱钩 74 分说明模型有基础能力但在陌生任务上掉点明显。这时候该做的不是把脱钩评测集换掉而是分析哪些任务类型掉分最多然后针对那些能力做改进。如果一个模型在脱钩评测里分数从 50 分提升到 68 分即使同分布评测从 90 分降到 85 分那它在泛化能力上也是明显进步的。真正的生产部署看的是后面的数字而不是训练环境内那个更漂亮的分。4.3 用对话评测集构建来对照说明拿对话评测集构建举个例子。假设训练环境是中文客服对话模型在同分布评测里准确率 88%。构建脱钩评测集时加入英文邮件回复、多轮追问、工具调用混合场景模型准确率降到 62%。这时候不要急着否定评测集而要看英文任务掉分是训练数据本身缺少英文还是模型编码器不支持多轮追问掉分是记忆模块上限低还是策略根本没学会追问工具调用掉分是接口格式问题还是动作空间在评测时新增了 ask_clarify 导致的每一个问题都能拆成可改进的技术项。脱钩评测的价值就在这里它能告诉你该往哪个方向努力而不是只给你一个高分幻觉。5. 脱钩方案的常见坑分数下降、评测不稳定、任务难度失衡5.1 分数下降先排查的不是模型而是评测集脱钩之后遇到分数下降先不要改模型按顺序排查评测集构建是否合理。评测任务里有没有包含无法完成的逻辑有没有因为任务模板太少导致抽样不均衡评测协议有没有偏移。最大步数、随机种子、解析规则和上一次是否一致环境初始化是否有泄漏。评测环境是否错误地加载了训练配置日志里环境 ID 是否属于 eval 配置模型是否做了缓存。如果评测时把之前的输出缓存当成了正确答案也会导致分数异常。我的经验里很多分数下降问题最后查出来是评测脚本的配置串了不是模型真的变弱了。所以先看评测链路再动模型参数。5.2 评测不稳定大概率是任务抽样和随机种子没锁住评测不稳定一种情况是每次抽到的评测任务难度差别大。比如评测集总共 200 题每次随机抽 50 题但两个子集难度不一致分数自然波动。建议评测固定整套任务或者用分层抽样保证每次都有各个难度档位的题。另一种情况是环境随机种子没固定。比如智能体的初始状态每次不同动作结果也带随机性那分数方差就会很大。评测协议里必须固定所有能固定的随机源至少固定环境种子、任务顺序、初始状态。模型内部的随机性可以根据需要控制但环境侧一定要锁住。5.3 任务难度失衡会让脱钩失去意义如果评测集全是特别简单的任务脱钩评测分数很高容易误以为泛化很好。实际上评测集没有区分度。反过来如果评测集全是从未见过的高难度任务模型几乎全失败也很难看出哪部分能力在进步。更好的做法是给评测任务分层L1和训练任务结构相似但数据不重叠L2任务目标相似但约束条件和工具范围有变化L3任务目标和交互方式都有明显变化训练时可以看 L1判断基本能力有没有保留重点看 L2反映中等迁移能力L3 可以少一些作为挑战项。这样脱钩评测就不只是一个分数而是一组能定位问题的分档指标。5.4 我的排查顺序把常见问题排成链路先看现象是分数低、不稳定还是完全无法运行。再看输入评测集任务格式、文本内容、工具数量、任务数量是否正常。再看环境是否加载了 eval 配置环境 ID 是否正确奖励函数是否被训练环境覆盖。再看协议随机种子、最大步数、重试次数、超时时间、解析规则是否锁定。最后看模型是否过拟合训练环境是否对某些状态特征有强依赖。按这个顺序排查多数问题都能定位。不要一上来就调模型结构或超参因为评测体系本身不稳的时候调模型只会让结论更模糊。回到开头那个问题。做 AgentMercury 这类智能体实验最该盯住的不是评测分数涨了多少而是评测分数还相不相信。训练环境和评测集脱钩看着像给测评加难度实际上是逼着模型去学更通用的策略。踩过几次坑之后我发现真正让模型在陌生环境里站得住的不是更多训练技巧而是你用什么标准去测量它。建议先从最小规模的训练环境和独立评测集开始把两套配置写清楚再逐步扩大任务难度。