AI渐进编程之四:状态机如何约束 AI 的动作?
前面三篇我们已经把三件事讲清楚了:
- 小任务可以直接用 prompt
- 任务复杂了,需要加 Harness
- 任务开始需要长期推进时,就要引入状态
到了这里,问题就变成了:
状态到底怎么组织?系统怎么从一个阶段走到下一个阶段?
这就是状态机要解决的事。
在这本书里,状态机不是为了“显得高级”,而是为了把“现在在哪里、下一步能做什么、什么算通过”写成可检查的规则。
只有这样,AI 编程才不是凭感觉乱跑,而是能沿着明确的转移关系继续推进。
1. 为什么需要状态机,而不只是状态?
如果只有状态,没有状态机,那么系统就只能记住“现在是什么样子”,但不知道:
- 为什么会走到这里
- 下一步允许什么动作
- 什么时候可以转过去
- 什么时候应该停下来
换句话说,状态只是静态事实,状态机才是动态关系。
这很重要,因为 AI 编程里的任务不是静止的。
它会经历:
- 读取任务
- 分析边界
- 修改内容
- 检查结果
- 记录反馈
- 决定是否继续
如果没有状态机,这些动作就很容易变成散乱的步骤。
有了状态机,系统就能把这些步骤串成一条清楚的转移链。
2. 状态机最核心的三个问题
状态机本质上只回答三个问题:
2.1 现在在哪
系统当前处于什么状态?
比如:
- 任务待处理
- 正在分析
- 正在修改
- 正在验证
- 已提交
- 被阻断
2.2 下一步能做什么
在当前状态下,允许哪些动作?
比如:
- 允许读取
current_task.md - 允许修改
paper.md的引言 - 不允许修改摘要和结论
- 允许记录
open_issues.md
2.3 什么算转移成功
什么条件满足后,系统才可以进入下一状态?
比如:
- 修改范围正确
- 主张强度没有增强
- 状态文件已同步更新
- 验证通过
这三个问题一旦讲清楚,状态机就有了。
3. 论文修改里的状态机例子
这本书一直用论文修改来说明问题。
比如当前任务是:
“只修改引言,降低过强的主张。”
那它对应的状态机大概会这样走:
3.1 Ready
刚收到任务,还没开始。
系统要先确认:
- 当前任务是什么
- 允许范围是什么
- 有没有已知问题
3.2 Analyzing
开始分析任务边界。
这一步通常会看:
- 引言里哪些句子主张太强
- 哪些内容可以改
- 哪些内容不能碰
3.3 Editing
开始执行修改。
这时系统只能在允许范围内动作。
比如只改引言,不动摘要、方法和结论。
3.4 Validating
修改完成后进行检查。
要确认:
- 是否只改了授权部分
- 主张是否被适度弱化
- 状态文件是否更新
3.5 Committed
通过验收,进入已提交状态。
这意味着当前轮任务完成,系统可以进入下一轮。
3.6 Blocked
如果发现越界、冲突或验证失败,系统就不能继续推进。
这时要记录失败原因,而不是假装没事。
4. 一个状态机,应该怎么写得像样?
状态机最重要的不是图画得多复杂,而是边界清楚。
可以先用最简单的形式理解:
Ready -> Analyzing -> Editing -> Validating -> Committed \-> Blocked这个图不复杂,但它已经表达了本书最关键的思想:
- 任务不是一次性完成的
- 每一步都要有前提
- 每一步都要能检查
- 失败不能消失,要进入阻断状态
这和“直接 prompt 一把梭”完全不同。
5. 状态机为什么比“随便写写状态”更可靠?
因为它把“状态之间的关系”显式化了。
如果只是写几个状态名,系统还可能:
- 乱跳状态
- 跳过验证
- 忽略失败
- 把临时结果误当成最终结果
但如果有状态机,就意味着每个状态都有:
- 进入条件
- 允许动作
- 转出条件
- 失败分支
这就让系统更像一个工程系统,而不是一个聊天记录合集。
6. 状态机和 Harness 的关系
这一点很容易混。
Harness 负责什么?
- 控制本轮动作
- 检查当前结果
- 限制可执行范围
- 记录失败和反馈
状态机负责什么?
- 定义阶段之间怎么转
- 定义什么时候能进入下一步
- 定义失败后该去哪里
- 定义哪些状态之间不能乱跳
可以这样理解:
- Harness 是执行层的控制器
- 状态机是控制层的骨架
没有状态机,Harness 容易变成一堆临时规则。
没有 Harness,状态机又只是纸面结构,落不到实际动作上。
7. 为什么状态机要写成可检查的规则?
因为 AI 编程不能只靠“人看起来合理”。
很多任务表面上像是做对了,实际上:
- 改了不该改的地方
- 没有保留证据
- 把问题藏起来了
- 只是暂时没爆出来
状态机的价值就在于:
它要求系统把“应该怎么转”写出来,把“为什么能转”检查出来。
这样,系统不是靠印象推进,而是靠规则推进。
8. 一个最小的状态机结构
如果把它写得更工程一点,可以先有这样的结构:
states:-ready-analyzing-editing-validating-committed-blockedtransitions:ready -> analyzing:condition:task_loaded == trueanalyzing -> editing:condition:scope_defined == trueediting -> validating:condition:diff_generated == truevalidating -> committed:condition:validation_passed == truevalidating -> blocked:condition:validation_failed == true这里的重点不是 YAML,而是它表达了一个清楚的事实:
- 不是任何状态都能跳
- 不是任何动作都能做
- 不是任何失败都能忽略
9. 状态机最容易出的问题
状态机如果写不好,也会变成负担。
常见问题有三个:
9.1 状态太多
状态分太细,反而没人维护。
9.2 转移太乱
状态之间允许的路径太复杂,最后谁也记不住。
9.3 失败分支不清楚
如果失败后不知道去哪,系统就会卡死或者乱跳。
所以,状态机不是越复杂越好。
它应该服务于任务推进,而不是服务于形式感。
10. 本章小结
这一章想说明的核心很简单:
状态机的作用,是把“当前在哪里、下一步做什么、什么算通过”写成明确的转移规则。
这样,AI 编程才不会只是“看起来在推进”,而是能够在一轮一轮的检查和反馈里,真正沿着可控路径继续往前走。
下一章,我会继续讲:状态更新与收敛,以及为什么循环里的反馈比一次性输出更重要。
