最近,关于 token 比人力贵的吐槽多了起来,有些公司发现,AI Agent 并不一定省钱。
就此,国外AI博主 Avi Chawla 拿 Claude 的真实数据算了笔账,结果吓人一跳。
一个30分钟的编码会话,92%的token走的都是缓存,直接干掉 81% 成本。
因为每次跟Agent对话,前面那些系统指令、工具定义、上下文,几乎都会重复。
搞不懂的是,像公司文档、产品资料这种不变的素材,为什么每次都去RAG?Agent为什么不去做缓存优化?也难怪调用token 是在烧钱。
以下为Avi Chawla的博文——
《大语言模型中的提示词缓存详解》
一则关于 Claude如何实现92%缓存命中率的案例分析
AI 智能体每执行一步操作,都会将完整对话历史回传给大语言模型。
这其中包含系统指令、工具定义,以及三轮对话之前已经处理过的项目上下文。每一轮交互,所有内容都会被重新读取、重新计算、重新计费。
对于长期运行的智能体工作流而言,这类冗余计算,往往是整套 AI 架构里成本最高的部分。
一段包含 20000 token 的系统提示词,重复运行 50 轮,就会产生100 万 token 的全额计费冗余计算,且不会产生任何新价值。该成本还会随着用户数量、对话场次不断叠加。
解决办法就是提示词缓存。但想要用好这项技术,需要先理解底层运行原理。
静态上下文与动态上下文
想要优化提示词,首先要区分内容中可变与不可变的部分。
每一次智能体请求都包含两个本质不同的部分:
• 跨轮次完全不变的静态前缀:系统指令、工具定义、项目上下文、行为规范。
• 随轮次不断新增的动态后缀:用户消息、模型回复、工具返回结果、终端运行信息。
正是这种结构划分,让提示词缓存得以实现。平台底层会存储静态前缀对应的模型计算状态,后续所有包含相同前缀的请求,都可以直接跳过重复计算,从内存中读取已有结果。
理解这一点后,本文所有架构设计思路都会一目了然。
KV 缓存的工作原理
想要明白缓存效果为何显著,需要先了解 Transformer 模型处理提示词的完整过程。
大语言模型每一次推理请求都分为两个阶段:
•填充阶段(Prefill):处理全部输入提示词。
对上下文内所有 token 执行密集矩阵运算,生成模型内部特征表征。该阶段计算量大、算力消耗高。
•生成阶段(Decode):逐一生成新 token。
每一个新 token 接入序列后,模型预测下一个 token。该阶段主要读取历史计算结果,计算量小,受内存限制。
在填充阶段,Transformer 会为每个 token 计算三组向量:查询向量 Query、键向量 Key、值向量 Value。
注意力机制依靠这三组向量,计算各个 token 之间的关联关系。任意 token 的 Key、Value 向量仅由其前方的 token 决定,一旦计算完成便固定不变。
无缓存机制时,每次请求结束后这些 Key、Value 张量都会被丢弃,下一次请求需要全部重新计算。以 20000 token 的前缀为例,大量本可复用的注意力计算被重复执行。
KV 缓存解决了该问题:将上述张量持久化存储在推理服务器中,并以 token 序列的加密哈希值作为索引。当新请求携带相同前缀时,哈希值匹配成功,直接从内存加载对应张量,完全跳过该部分 token 的填充计算。
该优化将单个生成 token 的计算复杂度从 O(n²) 降至 O(n)。对于重复 50 轮的 20000 token 前缀,计算量优化效果极为显著。
成本分析
计费规则决定了该架构优化的实际价值。
• 缓存读取价格为基础输入单价的 0.1 倍,即每个缓存 token 享受 90% 折扣
• 缓存写入价格为基础单价的 1.25 倍,存储 KV 张量需额外支付 25% 溢价
• 一小时延长缓存有效期,价格为基础单价 2.0 倍
以下为 Anthropic 旗下各 Claude 模型的对应计费情况。
上述成本优势成立的前提,是维持高缓存命中率。最典型的落地应用案例就是 Claude Code。
Claude Code 30 分钟编程实战案例
Claude Code 的设计核心目标仅有一个:保持缓存活跃。
以下从计费角度还原真实 30 分钟编程对话全过程:
第 0 分钟
Claude Code 加载系统提示词、工具定义、项目 CLAUDE.md 文件。
整体内容超 20000 token,全部为全新内容,是本次对话全程成本最高的时刻,该费用仅需支付一次。
第 1~5 分钟
用户下达指令,Claude Code 调用探索子智能体遍历代码库、打开文件、执行检索指令。
所有新增内容全部追加至动态后缀。而 20000 token 的静态前缀已走缓存读取,单价从 3.00 美元/百万 token 降至 0.30 美元/百万 token。
第 6~15 分钟
规划子智能体接收精简摘要信息,而非原始返回结果,避免动态后缀无意义膨胀。模型生成开发方案,用户确认后,Claude Code 开始修改代码。
每一轮交互均从缓存读取静态前缀,缓存命中率突破 90%,且每次读取都会重置缓存有效期,维持缓存活跃状态。
第 16~25 分钟
用户提出修改需求,触发更多工具调用、终端输出,动态后缀持续累积内容。
本次对话累计处理数十万 token,但每一轮交互均复用缓存中 20000 token 的基础前缀内容。
第 28 分钟
用户在终端查看费用。若无缓存,调用 Sonnet 4.5 模型处理 200 万 token 需花费 6.00 美元。
本次缓存效率达 92%,其中 184 万 token 为缓存读取,最终总费用仅 1.15 美元,单任务成本降低 81%。
这就是活跃缓存的实际效果:仅需一次性支付静态基础内容费用,后续均可低价复用,仅动态新增部分正常计费。
基于哈希缓存的局限性
提示词缓存最反常识的一点:
1 + 2 = 3 可命中缓存,2 + 1 则缓存未命中。
底层机制会对完整从头开始的 token 序列做哈希计算。只要序列内任意内容改动,哪怕仅调换两个元素顺序,哈希值就会改变,整段前缀都需要全额重新计算。
这并非细微的实现细节,而是约束条件,Claude Code 所有工程设计均围绕此约束展开。
以下为生产环境中真实导致缓存失效的案例:
• 系统提示词中插入时间戳,导致每次请求哈希值均不同
• JSON 序列化工具在不同请求中调整工具结构键值排序,前缀全部失效
• 对话中途更新智能体工具参数,20000 token 缓存全部清空
由此总结三条使用原则:
1. 对话全程不修改工具。工具定义属于缓存前缀内容,增删工具会导致后续全部缓存失效。
2. 对话中途不切换模型。缓存与模型一一绑定,中途切换低价模型需要重建全部缓存。
3. 不修改前缀内容来更新状态。Claude Code 不会改动系统提示词,而是在用户消息末尾追加标记,保证前缀内容固定。
应用到自研智能体开发
无论使用 Claude Code,还是从零搭建自研智能体,以上规则全部通用。
提示词按如下顺序排版:
1. 顶部放置系统指令与行为规则,对话全程不改动
2. 一次性加载全部工具定义,不中途增删
3. 紧接着放置检索上下文与参考文档,单轮对话内保持固定
4. 底部放置对话历史、工具返回结果,作为动态后缀
调用 Anthropic API 开启自动缓存后,随着对话推进,缓存分界点会自动向后延伸。
若未开启自动缓存,则需要手动划分 token 边界,边界划分错误会直接无法命中缓存。
当上下文长度即将达到上限时,可使用缓存安全分支压缩方案:保留原有系统提示词、工具、对话历史不变,仅新增一条上下文压缩指令作为消息追加。前缀缓存完全复用,仅新增的压缩指令 token 需要计费。
想要校验缓存是否正常生效,可监控 API 返回的三个字段:
• cache_creation_input_tokens:写入缓存的 token 数量
• cache_read_input_tokens:从缓存读取的 token 数量
• input_tokens:未走缓存、正常计算的 token 数量
缓存效率计算公式:
缓存效率 = cache_read_input_tokens ÷ (cache_read_input_tokens + cache_creation_input_tokens)
需要像监控服务可用性一样持续跟踪该指标。
核心总结
提示词缓存并非简单开关功能,而是需要整体架构围绕其设计的开发准则。
核心原理十分简单:提示词结构上,静态内容居上,动态内容向下新增。平台对前缀做哈希存储、保存 KV 张量,后续每次读取均可享受高额折扣。
真正的难点在于细节规范:不向系统提示词插入时间戳、不随意调整工具定义顺序、对话中途不切换模型、不改动缓存分界点之前的任何内容。
Claude Code 实现了规模化落地,达到 92% 缓存命中率、81% 成本降幅。若你正在开发智能体,却没有围绕提示词缓存做架构设计,将会错失大量成本优化空间。
热门跟贴