很多人看账单发现输入 token 比预想贵一截,却说不清钱花在「重复传的那段」还是「反复算的那段」。这篇不解释名词来源,只讲两件事:两类缓存的命中条件差在哪、命中之后省的是哪一笔;再给一套从日志到改法的排查顺序,方便你按自己接口的口径去核对。
很多人翻账单时发现输入 token 比预想贵一截,却说不清钱到底花在「重复传的那段」还是「反复算的那段」。这两个说法经常被混着用,实际触发方式、省钱位置都不一样。搞混了,优化动作就会打偏。
这篇不考据名词来源,只讲两件事:两类缓存的命中条件差在哪、命中之后省的是哪一笔;再给一套从翻日志到改提示的排查顺序。具体单价和门槛各家常变,一律以站内页面当时写的口径为准。
命中条件差在哪:稳定前缀还是整段复用
先分清缓存挂在哪个位置。一类是服务端把你在多次请求里重复传的前缀记下来复用,你传的字节没变它就还能用;另一类是你在会话里主动复用的上下文对象,由你自己的代码决定带哪一段。触发点不同,失效方式也不同。
最核心的变量是「前缀是否逐字节一致」。开头改一句话、换掉系统提示、插一个当前时间戳,后面全部跟着失效。换句话说,要省的那段必须放在最前面且保持稳定,越靠前越值钱。
- 前缀一致性
- 从第一个字符起连续相同才算复用,中间插一个变动字符,其后全部重新计算
- 最小长度门槛
- 太短的提示不值得缓存,门槛各家不同,别拿旧印象套
- 时间窗
- 缓存有存活时间,跨窗口后可能失效,长间隔调用要留意
- 同一份提示在两次请求间改动越小,命中越稳;变的是尾部追问,通常不影响前面那段的复用
- 把系统提示、固定知识片段、代码库说明放在最前面,把用户本轮问题放在最后
- 不确定某段是否被复用,就复制两次请求的前缀做逐字符比对,肉眼看不出的空格和换行最常见
省钱位置:省的是读入那笔,不是输出那笔
缓存一般作用在输入侧:命中后按更低的读入单价计,写缓存那一次可能另有单价。读、写、未命中三种情况是三个价格,不是一回事,细节看 /cache-write-read-usage-fields。
| 计费项 | 是否受缓存影响 | 优化方向 |
|---|---|---|
| 缓存读入 | 是,命中后单价更低 | 让前缀稳定、重复出现 |
| 缓存写入 | 可能另有单价,别忽略 | 减少反复重建,别频繁改前缀 |
| 未命中输入 | 按常规输入计 | 先确认是不是前缀在变 |
| 输出 token | 通常不受缓存影响 | 缩短回答、限制长度、换更合适的模型 |
真正省钱的前提是「同一大段前缀被反复使用」。长系统提示、固定知识片段、代码库说明,这类内容在多轮对话或批量任务里复用,才划算。输出那笔想省,得靠缩短回答、限制长度、去 /model-select 看模型边界,跟缓存无关。
先查日志再改提示:一套排查顺序
别凭感觉判断有没有命中。用量日志里通常有缓存相关的独立字段,字段含义参考 /usage-log-fields。字段全为零,说明根本没命中,先查前缀;字段有值但总价没降,问题多半在写入那笔。
- 翻用量日志找出缓存读入、写入字段是否非零,确认是真命中还是零命中,字段含义去 /usage-log-fields 对
- 比对前缀把同一批请求的前缀排在一起,标出每次都在变的那几行,常见元凶是时间戳、随机 ID、每次重排的示例
- 调整结构稳定内容前置、变动内容后置,结构化写法可参考 /prompt-structured,避免把动态内容混进头部
- 小批量对照跑一轮对照,看命中率与总价变化,再决定要不要铺开;效果不明显就别硬改,改回去也是成本
- 改动前先备份一份原提示,回滚时不用重拼
- 对照时固定其他变量,只动前缀位置,否则分不清是谁的功劳
- 连续观察几轮再下结论,单次波动不代表趋势
什么情况下不用折腾缓存
短提示、一次性任务、每次输入都不同的场景,加缓存基本没有收益,投入的时间不如去调提示本身。对结果一致性要求高、需要每次重新推理的任务,缓存带来的差异要自己评估,不行就关掉。
多模型路由的架构下,缓存往往按模型或按渠道隔离,切来切去会把命中打散。路由策略参考 /multi-model-routing-fallback,如果命中率一直上不去,先怀疑是不是路由把前缀切碎了。
- 提示总长度很短:先算门槛,不达标就别管缓存
- 每次前缀都不一样:先做结构梳理,再谈缓存
- 任务要求每次完全重算:缓存带来的差异要自己评估,不合适就关
- 渠道频繁切换:命中会被打散,先稳定主渠道再说
缓存省的是「重复的那一段」,不是「所有输入」;先找到重复,再谈命中。下一步拿你手上一批真实请求,按 /cache-write-read-usage-fields 的四项口径算一遍单次成本,再对照 /usage-log-fields 看日志字段,判断这笔优化值不值得做。想横向比各家官方 API 的当前单价与口径,去 /price-watch 核对当时的数字。→
常见问题
两类缓存是不是只能选一个用?
不是二选一。它们作用位置不同,一个偏服务端自动复用前缀,一个偏你在请求结构上主动复用上下文;同一个请求里可能都涉及。关键是先看你调用方实际记的是哪几项计价字段,再决定改哪里。
为什么我改了提示词,账单反而涨了?
常见原因是改动让前缀不再一致,命中没了,输入又按原价算;如果还涉及缓存写入的单价,那一次会更贵。改提示前先把旧版本跑一批留底,改完对照命中字段和总价,别只看单次结果。
命中率肉眼看不出来,怎么确认?
看用量日志里缓存相关字段的数值,而不是体感。字段名各家不同,去 /usage-log-fields 对一遍自己后台的列;没有这些字段就说明你这条链路没记录,先补日志再谈优化。