本页目录
批量加载的问题
现状的做法
要教会前沿模型 agent 干一件事,最常见的做法是写一份 markdown 文件(也就是一个 "skill"),
放进 .claude/skills/ 这类目录里,等 agent 判断相关时再把它注入 system prompt。
Anthropic 的 SKILL.md 格式
就是这种做法的代表。一个 skill 一般包含 100–500 行说明文、YAML frontmatter,再加几个例子。
在小规模下这套做法没什么问题:5 个 skill 几乎察觉不到成本,50 个时已经能感觉到压力,到 500 个 agent 就直接崩了。
三种可以量化的失败
失败 1:token 成本只跟 skill 数量挂钩,跟任务复杂度无关
每一轮都把所有"可能相关"的 skill 一股脑加载进来。60 个 skill、每个平均 200 行, 就是大约 30k token 的上下文,全砸在 agent 可能根本用不上的知识上。 多数对话其实只用到一两个 skill 的内容,但要为全部 60 个买单。
# A real measurement (frontend-design corpus, v3 benchmark)
Bulk-loaded skills: 60 SKILL.md × ~200 lines = ~30 KB context
Skill Wiki index: 980 atoms × ~30 tok summary line = ~3 KB context
Atom bodies on demand: = ~600–2,000 tok per turn
Saving: ~10 × index reduction
~6 × typical-turn token cost 失败 2:上下文污染比上下文预算更要命
只盯着"token 预算"会忽视真正严重的问题:错的 token 一旦进了 prompt,会主动把模型带偏。 把一份"OWASP 输入校验"的 skill 塞进一个写邮件文案的 prompt 里, 损失的不只是 token,模型还会被推向一种带安全味道的语气,整个回答都会跑偏。 我们在同一份 20 任务基准上对比批量加载和按需加载,质量分相差 −13。
一份 200 行的 markdown 是一整块、没有边界。哪怕你只想用其中三条 fact 加一条 rule, 也只能整块加载。粗粒度知识加上急加载,就是这种典型的失败模式。
失败 3:skill 之间没法有意义地互相引用
在 SKILL.md 格式下,两个 skill 之间的关系顶多是一条"see also"超链接。 没有任何机器可校验的方式去表达"这条 rule requires 那个 term"、 "这个 pattern contradicts 那个 anti-pattern",或者 "这个 example validates 那条 fact"。 校验器因此抓不到矛盾,检索器没法顺着依赖走,chunker 也没有 kind 这一层概念来判断什么该留、什么该丢。
结果就是 skill 越来越像 JavaScript:一团没有类型的东西,只是恰好在作者测过的场景里跑得通。
替代方案需要满足什么
替代方案需要同时具备这三点:
- 原子粒度。知识单元要小到可以单独加载, 不是"一个 skill",而是一条 fact、一条 rule、一个 pattern、一个 method。
- 带类型的边。原子之间的关系要用带类型的 verb 来表达
(
requires、validates-with、contradicts), 这样校验器才能推理,检索器也才能顺着走。 - 惰性投影。agent 要能先看到有哪些原子存在(这是便宜的), 而不必加载它们的正文(这是昂贵的)。等检索挑出目标后,再按 id 按需加载。
延伸阅读
- Field note:Prime vs SKILL.md graphs——批量加载为什么输了
- Prior art:与 RAG、知识图谱、agent skills 的对比