第 32 课:长时程执行与状态

第 31 课把"怎么在巨大空间里搜、什么时候砍方向"讲完了;这一课只追一个问题:没人看着跑 23 小时,Agent 凭什么不跑偏、状态放哪、什么时候该停。我们从一条真实的 23 小时自主实验曲线讲起,把 best-so-far 曲线、项目状态外置(File-as-Bus)、失败诊断、环境隔离、token 成本账与停机判据,一路算到工程细节。

🎯 学完这 6 步你将能够:
① 用 best-so-far 曲线与 held-out 准入判断一条长时程任务有没有"越跑越好"
② 说清项目状态为什么要落在文件里(File-as-Bus),以及去掉它会掉多少分
③ 用"并发 × 单任务显存"估资源、用"证据条件"决定继续、改向还是终止
🗺 本节推理链(6 步逻辑递进:从"凭什么不跑偏"到"什么时候该停")
1要让一个 Agent 在没人盯的情况下连续自主跑 23 小时、74 轮实验,这就要求它的成绩曲线必须越跑越好——每轮把结果写进 context 之外的项目状态,再用 held-out 准入挡住刷分。长时程要看越跑越好。
↓
2既然「长时程要看越跑越好」,所以成绩只能靠状态累积——这就要求把决策相关的状态从易失的 context 里搬进持久文件,用「状态落在上下文之外」的方式让每一轮都能接着上一轮。状态落在上下文之外。
↓
3既然「状态落在上下文之外」,那么状态一旦持久,失败就不再白费——这就要求跑挂的时候能定位"错在哪一环",把坏轮次的日志写回文件(而非留在 context)供下一轮读。失败要能诊断复用。
↓
4既然「失败要能诊断复用」,那么并行跑多个假设就必须互不污染——这就要求一个假设一个隔离工作树(worktree,指 git 的独立工作目录),再把资源预算落到每轮的 tokens 与显存上。执行环境要隔离。
↓
5既然「执行环境要隔离」,那么并发的每个执行器都在烧预算——这就要求把账算平:轮数 × 单轮 tokens × 并发度,并对照第 26 课的 4×/15× 口径。成本要按 token 算。
↓
6既然「成本要按 token 算」,那么预算有限时就得知道何时收手——这就要求用证据条件三选一:continue / revise / terminate,把「该停就停」变成可执行判据。该停就停。
长时程执行best-so-farFile-as-Busworktree 隔离token 成本证据条件终止
1
跑 23 小时没人看着,怎样才算没跑偏?
提示:别只看它最后跑出多高——先看这条曲线中间有没有"越跑越好",还是原地打转。
▾
知识背景
长时程 ML 研究工程(long-horizon ML research engineering,指把研究规格变成能跑、能验证的系统)的核心难点是延迟反馈——跑完一整轮才知道对不对。AiScientist(Chen 等,arXiv:2604.13018,2026)报告了一条真实曲线:在 MLE-Bench Lite 的 Detecting Insults 任务上,系统连续自主运行 23 小时、做了 74 轮实验(无人工干预),验证 AUC 从 0.903 升到 0.982,中途发生 18 次 best-so-far 更新。

第 31 课我们把"怎么在巨大空间里搜、怎么砍方向"讲完了;这一课换个视角:让它自己长跑,凭什么不跑偏?

因为长时程最怕的不是单步慢,而是"跑了半天越跑越差还没人发现"。判断力来自一条可审计的曲线。每轮把结果写进 context(模型上下文,即模型这一次能看到的全部 token)之外的持久状态。并且只在 held-out(预留测试集,即不参与搜索的那部分数据)上变好,才计入 best-so-far(至今最好成绩)。这样曲线才会单调向上。就像长跑要看配速表,不是看某一步迈得多大;配速乱了,越跑越远也没用。所以先把这条曲线读出来。

🧮 第一笔账:一条 23 小时曲线的四个读数
Step 1:原始读数
读数数值来源
连续自主运行23 小时arXiv:2604.13018 图 1
无干预实验轮次74 轮同上
best-so-far 更新次数18 次同上
验证 AUC0.903 → 0.982同上
算术无关的一条口径:四个读数出自同一张图、同一条 run;AUC 是"越接近 1 越好"的排序质量指标。这不是示意值,是论文读数。
Step 2:更新密度与 AUC 增幅
算式结果
更新密度 = 18 ÷ 74≈ 0.243 → 24.3% 的轮次产生新最优
AUC 绝对增幅 = 0.982 − 0.9030.079
AUC 相对增幅 = 0.982 ÷ 0.903≈ 8.7%
算术:74 轮里只有约 24.3% 的轮次刷新了最优——大部分轮次是"试错没成",这正是长时程的常态;但 0.079 的绝对提升说明"没成"的轮次也在被累积利用。
Step 3:轮均耗时(换算)
项算式结果
总分钟数23 × 601,380 分钟
轮均耗时1,380 ÷ 74≈ 18.6 分钟/轮
含义每 18.6 分钟才回一次信号
算术(换算):23 小时 ≈ 1,380 分钟,摊到 74 轮约 18.6 分钟/轮。延迟反馈的单位是"十几分钟",不是"一次 API 往返"——这是长时程和普通对话最根本的区别。
🎯 关键认知

判断长时程跑得好不好,先看三件事:曲线是否单调向上(靠 best-so-far)、新最优是否只在 held-out 上准入、每轮回信号要等多久。23 小时 / 74 轮 / 18 次更新 / AUC 0.903→0.982 给出的就是一条"越跑越好"的证据链。

AI 助教
👋 对"越跑越好"有疑问?比如「best-so-far 到底指什么」「held-out 为什么不能搜」?

说清你的任务,我帮你判断一条曲线算不算在累积。
2
状态放哪?上下文装不下怎么办?
提示:一次运行 74 轮,历史越来越长——它是把全部历史塞进 context,还是把状态放到别的地方?
▾
知识背景
File-as-Bus(文件当总线,指用持久文件在多个角色、多次调用之间传状态)是 AiScientist(arXiv:2604.13018)的核心机制。它的 schema(结构定义)把工件分成三种更新模式:append-only 日志(只追加、保时间序)、versioned 工件(保当前版 + 历史版)、mutable 状态(短命的控制信息)。论文消融显示:去掉 File-as-Bus,PaperBench 掉 6.41 分、MLE-Bench Lite Any Medal 掉 31.82 个点。

上一张卡片看到它在 74 轮里越跑越好;可 context 是易失的——一次调用结束就清空。状态放哪,才是长时程能不能接上的关键。

因为74 轮的历史、诊断、产物不可能全塞进窗口,硬塞只会挤掉真正要用的证据;正确做法是把决策相关的状态外置到文件,每轮只把"该看的那部分"读回 context,并在关键轮写一个检查点(checkpoint,即把当前状态快照落盘,便于中断后恢复)。就像项目交接不靠某个人的记忆,靠的是共享盘里的文档;人换了,文档还在。所以要把状态从"对话"搬进"文件总线"。

🧮 第二笔账:状态外置到底掉不掉分
Step 1:File-as-Bus 的三种工件
模式存什么为什么
append-only 日志实现日志、实验诊断证据不能覆盖
versioned 工件计划、分析、报告要当前版 + 可恢复历史
mutable 状态短命控制信息不必留历史、保持轻
算术无关的一条分工:该留的证据(日志)只追加,要演进的状态(计划)带版本,临时的控制(指针)可覆盖——三种模式对号入座。
Step 2:消融读数
基准去掉 File-as-Bus差额
PaperBench 分数下降−6.41 分
MLE-Bench Lite Any Medal下降−31.82 个点
MLE-Bench Lite 剩余81.82 − 31.82 = 50.00 个点
算术:论文报的 MLE-Bench Lite 是 81.82 Any Medal%,去掉 File-as-Bus 掉 31.82 → 只剩 50.00;相对下降 31.82 ÷ 81.82 ≈ 38.9%。去掉一层文件总线,Any Medal 掉了近四成。
Step 3:提升被吃掉多少(派生)
项算式结果
去掉 File-as-Bus 掉的 PaperBench 分6.41—
对照:相对最强基线的提升(单 backbone Gemini-3-Flash)9.92—
被吃掉的比例6.41 ÷ 9.92≈ 64.6%
算术(派生):去掉 File-as-Bus 掉的 6.41 分,等于把 9.92 的相对提升吃掉约 64.6%(9.92 为该行的单 backbone Gemini-3-Flash 取值,论文摘要报告的平均增益为 10.54)——文字与数字都表明持久状态是长时程的主要增益来源,不是锦上添花。
🎯 关键认知

上下文是易失的,项目状态必须落在上下文之外(File-as-Bus)。消融给出量化代价:PaperBench −6.41、MLE-Bench Lite Any Medal −31.82。判据是:换一个角色、换一次调用,它还能不能从文件里读回上一轮的证据。

AI 助教
👋 对 File-as-Bus 有疑问?比如「什么该写文件、什么留在 context」「三种工件怎么分」?

说清你的任务与角色数,我帮你定状态外置方案。
3
失败了它怎么自己爬起来?
提示:一轮失败后,它需要先知道"错在哪一环"——想想一条流水线里可能出错的环节有多少个。
▾
知识背景
AiScientist 的 evidence-driven research-engineering loop(证据驱动的研究—工程回路)说明:每轮实验产出可执行证据(失败、部分成功、指标缺口、瓶颈、结果偏差),Orchestrator(编排者,负责定策略的角色)据此选择下一种干预——补实现、改数据处理/配置、重跑实验,或在假设被推翻时退回更早的分析。论文把失败成因归到多层:论文解读、数据处理、模型设计、训练配置、基础设施,以及它们之间的交互。

上一张卡片把状态外置到了文件;状态一持久,失败就不再"白费"。那它到底怎么从失败里爬起来?

因为长时程的失败往往是沉默的——进程没崩,但指标不对,成因可能横跨论文解读、数据、模型、训练配置、基础设施好几层;这就要求每轮失败都被写成"诊断记录"(错在哪一环 + 依据),这就要求把它写回文件而不是留在 context 里,下一轮才谈得上修。就像医生看检验单:不先定位是哪个器官,开再多药也是碰运气。所以回路的关键不是"重试",是"先诊断再修"。

🧮 第三笔账:诊断—修正回路
Step 1:一条流水线的六类成因
层典型症状干预
论文解读方法与目标对不上退回分析、改假设
数据处理指标偏低但能跑修预处理
模型设计结构不匹配改实现
训练配置不收敛 / 波动调超参
基础设施OOM / 超时改资源
交互多个原因叠加分而治之
算术无关的一条映射:每类症状对应一种干预——诊断的价值就是把"重试"换成"对地方下手"。
Step 2:触发诊断的轮次(示意)
项算式结果
总轮次74—
假设首跑失败率(示意)40%—
触发诊断的轮次74 × 0.429.6 轮
算术(示意:失败率 40% 为假设值):74 轮里约 29.6 轮会触发诊断;失败不是异常,是常态——回路必须默认自己会失败。
Step 3:一次诊断要"烧"掉多少时间(示意)
项算式结果
轮均耗时1,380 ÷ 74≈ 18.6 分钟/轮
一次诊断 + 重跑(按 2 轮计)2 × 18.6≈ 37.2 分钟
对照"闷头重试"诊断省下的是后面 N 轮的无效盲跑
算术(示意:按 2 轮估算):一次诊断 + 重跑约 37.2 分钟;而"不诊断直接重试"要把同样的时间花在错误方向上。诊断的收益是"少跑的无效轮",不是"跑得更快"。
🎯 关键认知

失败要能被诊断成"错在哪一环",才能被复用。回路 = 产出证据 → 定位层级 → 选干预 → 写回状态;触发条件是"指标缺口 / 偏差",而不是"进程崩溃"。判定:它有没有把失败写成下一轮的输入。

AI 助教
👋 对失败诊断有疑问?比如「怎么知道错在哪一环」「诊断记录该写什么」?

说清你的流水线,我帮你把诊断步骤拆出来。
4
多个假设同时改同一份代码、抢同一块显存,会怎样?
提示:同一份证据里混进两个人的改动,出问题时你还分得清是谁干的吗?
▾
知识背景
Arbor(Jin 等,arXiv:2606.11926,2026)让每个执行器(executor)在隔离的 git worktree 里实现并测试单个假设——worktree(工作树)指 git 的独立工作目录,同一仓库可检出多份互不干扰的副本。只有通过 held-out 验证的改进才被"准入"回主干。论文报告:Arbor 在 MLE-Bench Lite 上以 GPT-5.5 达到 86.36% Any Medal(本文对比中的最强结果),并取得相对 Codex / Claude Code 超过 2.5× 的平均相对 held-out 增益。(注意:这两个读数是整套框架的结果,隔离本身的贡献论文未单独消融。)

上一张卡片讲失败怎么被诊断;但要是多个假设同时跑、还共用同一份代码,诊断就没了意义——A 的改动会污染 B 的证据。为什么要给每个假设一套隔离环境?

因为长时程常常并行搜索,多个执行器会同时改文件、抢显存;没有隔离,一个假设的失败会被误判成另一个的,反过来也一样。就像多人同时编辑同一份文档,谁改坏了都说不清;一人一份副本 + 合并审查才可控。所以一个假设一个工作树,再加资源预算兜底。

🧮 第四笔账:隔离与资源预算
Step 1:隔离的三道边界
边界隔离对象目的
worktree代码工作目录改动互不覆盖
工件目录输出 / 日志 / 模型证据归属清晰
资源配额GPU 显存 / tokens防止一个吃光全部
算术无关的一条原则:隔离要覆盖代码、工件、资源三层——只隔离代码,显存仍会互相饿死。
Step 2:并发 × 单任务显存 = 需要多少卡(示意)
项算式结果
并发任务数(示意)8—
单任务显存(示意)24 GB—
总显存需求8 × 24192 GB
按 48 GB/卡折算192 ÷ 484 张卡
算术:8 个并发 × 24 GB = 192 GB,按 48 GB/卡需 4 张卡。(并发数与单任务显存为示意值,用于说明"并发上限由资源预算反推"。)
Step 3:隔离 vs 共享
维度共享一份一假设一 worktree
证据可信互相污染可归因
失败定位难清楚
合并隐式覆盖显式准入
代价低多占磁盘
算术无关的一条取舍:隔离的代价是磁盘与调度开销,换来的是证据可归因、改进可准入——长时程里这笔交换划算。
🎯 关键认知

并发搜索的前提是失败互不污染,所以一个假设一套 worktree + 独立工件目录 + 资源配额。资源账 = 并发数 × 单任务显存 → 需要多少卡。判定:任意两条支线的证据能不能分别归因。

AI 助教
👋 对隔离有疑问?比如「worktree 和容器哪个合适」「并发开几个」?

说清你的硬件与任务,我帮你算并发与配额。
5
74 轮实验跑下来,时间与 token 各花了多少?
提示:时间是明账,token 是暗账——想想 74 轮里每轮要跟模型来回几次。
▾
知识背景
长时程的成本不在"一次调用",而在"轮数 × 每轮往返"。第 26 课引 Anthropic《How we built our multi-agent research system》(2025)给出 token 口径:普通对话约 1×,单 Agent 约 4×,多智能体约 15×(相对普通对话)。Arbor 也用 token 消耗与搜索成本做了分析(arXiv:2606.11926 §5.8)。

上一张卡片把并发折成了卡数;卡数背后是钱。这笔账怎么算才算得清?

因为长时程要跑 74 轮、每轮涉及多次模型往返,成本随轮数线性放大;只看"单次调用多少钱"会严重低估。所以要把账拆成 时间 × 并发 × 单价,并对照第 26 课的 token 口径。就像出差报销:不是看单张发票,是把交通、住宿、补贴乘天数一起算。所以先立一个可复算的成本公式。

🧮 第五笔账:74 轮的总 token
Step 1:轮数 × 单轮 token = 总 token(示意锚点)
项算式结果
轮数74—
单轮普通对话量(示意,承第 26 课 20,000 锚点)20,000 token—
总 token(1× 口径)74 × 20,0001,480,000 token
算术(示意锚点):以第 26 课的 20,000 token/次普通对话为锚,74 轮 ≈ 1,480,000 token。锚点来自第 26 课,倍数才是 Anthropic 口径。
Step 2:对照第 26 课的 4× / 15× 口径
口径单轮 token74 轮合计
普通对话 1×20,0001,480,000
单 Agent 4×80,0005,920,000
多智能体 15×300,00022,200,000
算术:承第 26 课口径(4× / 15×),74 轮下单 Agent ≈ 5,920,000、多智能体 ≈ 22,200,000 token;多智能体是单 Agent 的 22,200,000 ÷ 5,920,000 = 3.75 倍(15 ÷ 4 = 3.75)。
Step 3:时间账(与 token 账并列)
项算式结果
总秒数23 × 3,60082,800 秒
轮均82,800 ÷ 74≈ 1,119 秒/轮
含义时间账按小时,token 账按轮数——两者都要算
算术:23 小时 = 82,800 秒,轮均 ≈ 1,119 秒(约 18.6 分钟)。"跑得久"和"烧得多"是两笔账,必须同时给。
🎯 关键认知

长时程的成本公式 = 时间 × 并发 × 单价,其中 token 是暗账。对照口径(第 26 课):单 Agent ≈4×、多智能体 ≈15× 普通对话。判定:报一条 run 时,能不能同时给出小时数与总 token 数。

AI 助教
👋 对成本账有疑问?比如「74 轮要花多少 token」「4× 和 15× 怎么用」?

说清你的模型与步数,我帮你估一条 run 的账。
6
跑着跑着,什么信号说明该停、该换方向了?
提示:证据够了就发,证据不够就换;想想要连续多少轮没新最优,才该收手。
▾
知识背景
Arbor 把"是否继续"交给证据:一个候选只有在 held-out 评估上变好,才被提升为当前最优,否则该支线被剪(prune)。这种"证据条件"式控制可归纳为三选一:continue(继续)/ revise(改向)/ terminate(终止)。AiScientist 的 Orchestrator 也据工作区地图与已记录证据选择下一步干预,或在假设被推翻时退回分析。

上一张卡片把账算平了;账再平,也总得有个停的时候。什么信号说明该停?

因为长时程里"再多跑一轮"永远有诱惑(沉没成本 + 可能翻盘),但预算有限;把停与不停交给证据条件,比交给"感觉差不多了"可靠得多。就像考试到点就得交卷:不是不会写了,是时间到了;该交还是该再想,要有明确规则。所以把 continue / revise / terminate 写成可执行判据。

🧮 第六笔账:continue / revise / terminate
Step 1:三选一的判据
动作触发条件依据
continue近期仍有 best-so-far 更新证据在累积
revise连续多轮无更新且方向单一换支线 / 换假设
terminate预算触顶或 held-out 长期不升证据不足 + 成本已满
算术无关的一条映射:continue 看"有没有新证据",revise 看"方向是不是死了",terminate 看"预算 + held-out"——三者判据不同,不能混用。
Step 2:用更新密度定"该换方向"的阈值(示意)
项算式结果
平均更新间隔74 ÷ 18≈ 4.11 轮/次
容忍阈值(2× 平均间隔,示意)2 × 4.11≈ 8.22 轮
含义连续约 8 轮无 best-so-far → 触发 revise
算术(示意阈值):平均每 4.11 轮才刷新一次最优;若连续约 8.22 轮(2× 平均间隔)都没更新,就说明当前支线大概率走死 → revise。
Step 3:终止线(与预算挂钩)
信号含义动作
held-out 不升且预算触顶证据不足 + 成本满terminate
总 token 达上限钱花完terminate
仍有支线待试且预算未满有证据空间continue
算术无关的一条收口:终止 = 证据条件 + 预算条件同时成立;只要还有未试支线且预算未满,就该 revise 到那条支线,而不是草草 terminate。
🎯 关键认知

停机不是"感觉",是证据条件——continue / revise / terminate 三选一。用 best-so-far 的更新密度定"该换方向",用预算 + held-out 定"该终止"。判定:每一次收手都能说清触发的是哪条判据。

AI 助教
👋 对停机判据有疑问?比如「多少轮没进展该停」「怎么区分该换方向和该终止」?

说清你的任务与预算,我帮你定三选一判据。