大家好,我是十三!欢迎来到十三Tech。

最近用几款 AI IDE 时我发现一个现象:同样是 Claude 4,在 Claude CLI、Cursor 里的表现明显好于在 Trae 里——它对上下文的理解更准,生成的代码更贴业务,修 bug 也更快。我最初以为是模型微调的差异,直到读到 Manus 团队的《Context Engineering for AI Agents》,才意识到一件事:Agent 的竞争已经从「模型为王」转向「上下文为王」。

模型是公开的,谁都能调用;真正拉开差距的,是你喂给它的上下文怎么组织。这篇文章把上下文工程相对微调的优势、以及六条上下文设计原则梳理一遍。

一、微调,还是上下文工程

微调与上下文工程的取舍

微调改的是模型权重。

  • 优势:理论上能逼近更高的性能上限,让模型更懂某个特定任务。
  • 劣势:成本高、周期长(通常以周计)、迭代慢。更麻烦的是,等微调好的模型刚上线,基础模型可能已经换代,之前的投入直接作废。Manus 团队上一家公司就栽在这上面。

上下文工程不改权重,改的是每次请求带进去的上下文。

  • 优势:迭代快(小时级)、成本低、与基础模型解耦、可替换。
  • 劣势:性能天花板就是基础模型本身,对提示词设计和工作流编排要求更高。

Manus 的选择很明确:押注上下文工程。这样他们能以小时级速度发布改进,让产品「正交于」底层模型的迭代——用他们的话说,模型进步是上涨的潮汐,他们希望 Manus 是船,而不是焊死在海床上的柱子。

二、上下文工程的六条原则

上下文工程六条原则总览

下面六条是 Manus 团队四次重构 Agent 框架后总结出来的。

1. 守护 KV-Cache

守护 KV-Cache:前缀一动,缓存全碎

KV-Cache 命中率是衡量生产级 Agent 延迟和成本最关键的指标。

语言模型处理序列时,会为每个 token 计算并缓存 Key/Value(即 KV-Cache)。后续 token 可以直接复用这些缓存,不必重算——这同时降低首 token 延迟(TTFT)和成本。Agent 的工作模式是「长输入、短输出」,上下文越来越长,输出(通常是一次函数调用)却很短,Manus 给出的平均输入输出 token 比是 100:1。这种情况下缓存复用尤其关键:以 Claude Sonnet 为例,缓存命中的 token 成本只有未命中的十分之一。

怎么守住缓存:

  • 保持 prompt 前缀稳定。任何一个 token 变了,它之后的缓存就全部失效。常见错误是在 system prompt 里放精确到秒的时间戳——这是缓存的杀手。
  • 上下文只增不减。别修改历史记录,序列化逻辑要确定(比如 JSON 对象的 key 顺序固定)。

2. 屏蔽,而不是移除工具

工具集管理:屏蔽而非移除

Agent 能力越强,工具数量膨胀得越快。一个常见误区是根据任务,动态地在上下文里增删工具定义。

这么做有两个问题:一是工具定义通常排在 prompt 前部,改它就直接破坏了 KV-Cache;二是历史记录里可能已经有过对某个「已移除」工具的调用,模型会对着空气找不到目标。

正确做法是屏蔽(Masking):工具定义原样保留,在解码阶段把当前不该被选中的工具屏蔽掉。再配合统一的命名前缀——比如浏览器工具都叫 browser_*,命令行工具叫 shell_*——就能用简单的前缀匹配,把 Agent 的行为圈在某类工具里,不需要复杂逻辑。

3. 把文件系统当作无限上下文

哪怕是百万级的上下文窗口,在真实 Agent 场景里也常常不够用,而且长上下文会带来性能下降和成本上升。

网页、PDF 这类非结构化数据很容易把上下文撑爆。你又没法预判十步之前的哪个信息会在关键时刻派上用场,所以任何不可逆的压缩都有风险。

出路是把文件系统当成 Agent 的外部记忆体:容量无限、持久化,还能被 Agent 直接操作。核心思想是可恢复的压缩——网页内容可以丢弃,只要上下文里留着它的 URL;文件内容可以省略,只要留着它在沙箱里的路径。这样既压短了上下文,又不丢信息。

4. 用「复述」对抗遗忘

一些强 Agent 在执行复杂任务时,会建一个 todo.md 然后一步步更新它(Claude 的 TodoList、Kiro 的 Spec 都是同一个思路)。

在长达几十步的任务链里,Agent 很容易「迷失在中间(Lost-in-the-middle)」,忘了最初的目标。通过不断重写计划文件,Agent 相当于在每轮迭代的末尾,把全局目标和任务计划「复述」了一遍——把最重要的信息推到上下文的最末端,也就是模型注意力最强的区域,从而不偏离航道。

5. 保留失败轨迹

一个反直觉的做法:不要清理 Agent 的失败尝试

出错时,人很自然的反应是清掉错误日志再重试,给模型一个「干净」的上下文。但这等于剥夺了它从失败中学习的机会——模型看不到失败的尝试和返回的错误堆栈,就没法更新自己的判断,很可能在同一个地方反复栽跟头。

正确做法是保留完整的操作轨迹,包括失败的尝试和环境返回的错误。模型看到「这个动作失败了、原因是 X」,自然会降低再走同一条路的概率。错误恢复能力是衡量 Agent 鲁棒性的关键,但目前多数学术 benchmark 都没把它算进去。

6. 别掉进少样本陷阱

Few-shot 是提升 LLM 的常用手段,但在 Agent 场景里它会变成陷阱。

语言模型是很强的模仿者。如果上下文里塞了一长串相似的「动作-观察」对,模型会倾向于沿这个模式继续走,哪怕当前情况该换策略了。比如连续审 20 份简历时,Agent 可能越跑越机械,重复同样的动作,效率下降甚至产生幻觉。

应对办法是注入可控的、结构化的多样性:序列化时轻微改变模板、换措辞、调字段顺序。这点「噪音」能打破单调重复,逼模型每一步都重新判断,而不是惯性地模仿。

写在最后

上下文工程干的,是把模型从「能跑」变成「好用」的活:守护 KV-Cache、屏蔽而非移除工具、文件系统作记忆、用复述对抗遗忘、保留失败轨迹、避开少样本陷阱。这六条没有一条是花架子——每一条都直接对应 Agent 的延迟、成本或可靠性。

模型是潮水,上下文工程是船。潮水越高,对造船手艺的要求也越高。


关于十三 Tech

资深服务端研发工程师,AI 编程实践者。专注分享真实的技术实践经验,相信 AI 是程序员的最佳搭档。