☰
从Claude Code迁移到Pi:系统提示词从1.4万压到200,token成本暴降85%
2026/10/17 12:00:32 网站建设 项目流程

1. 先说说为什么会有人想从 Claude Code 换到 Pi

1.1 Claude Code 好用,但账单真的有如针刺

Claude Code 在编码助手圈子里名声不小,我试用过一段时间,它的交互设计确实讨喜:多文件修改、自动跑测试、还能自己排查报错,拿到一个仓库就能像真人一样干活。可问题也出在这里——它每干一件事,都会把一大堆系统提示词一起算进 token 消耗里。默认配置下,系统提示词动辄 1.4 万 token,你再接上一些长一点的上下文,每个会话的“固定支出”就摆在那里,不管模型干了多少正事,这部分钱都是要付的。

我做了一个很简单的测试:不写任何代码,只启动一个脚本,让它读一遍配置再退出。结果一个“什么都没干”的会话,账上已经走了两万多 token。看到账单的那一刻,我真有一种自己变成了冤大头的感觉。更难受的是,这些消耗里很大一部分不是模型“思考”出来的,而是被一个又长又重、每轮都要跟着请求一起发送的系统提示词吃掉的。

1.2 Pi 是什么,凭什么能替下 Claude Code

后来我在一个开发者小群里看到有人提到 Pi,说它是一个特别克制的终端 Agent——它的设计思路和 Claude Code 那种“全家桶”完全相反:Pi 把系统提示词当成一个可配置的、按需加载的模块,而不是默认塞满一整套风格规范、工具说明和示例输出。开发者可以自己决定这轮会话系统提示词到底放多少内容,甚至可以压到只剩几句核心规则。

这个思路让我眼前一亮。我需要的不是一个大而全的编码助手,我只需要一个能读代码、能跑命令、能改文件的最小骨架,其余能力完全可以通过“临时指令”在每一轮里按需求注入。换句话说,Claude Code 是“开局给你一整栋精装房”,Pi 则是“给你一间毛坯房,装什么隔断完全自己定”。对于想把 token 变量控制在自己手里的人,后者天然更友好。

2. 动手前,先解剖 1.4W 的系统提示词都去哪了

2.1 默认配置里塞了哪些“隐形”内容

很多人以为系统提示词就是最顶上那几句“你是一个编程助手”,其实不是。我用日志抓取的方式把 Claude Code 默认系统提示词完整导出来看过,里面大体包含这么几块:

  • 角色设定与价值观约束,通常占 3000 到 5000 token;
  • 工具调用格式说明,包含每个工具的参数示例、返回值约定,几千 token 很常见;
  • 十几条 few-shot 示例,每条都带着完整的多轮交互模板;
  • 编码规范、注释风格、测试要求等通用建议;
  • 循环执行的控制信息,包括如何判断任务完成、如何汇报进展等;
  • 多文件编辑、代码检索的提示模板和系统级安全约束。

这些内容单看都不算离谱,但它们加在一起,就会变成每轮请求都要携带的“固定重装备”。特别是当你只是想让模型帮你改一行代码的时候,这一万四千 token 的“行李”也全程跟着你跑——这就是账单虚高的根本原因。

2.2 哪些能砍,哪些不能砍

我针对每一块内容都会问同一个问题:这一块真的需要每一轮都出现吗?把这个问题想清楚,削减方案就非常清晰了。角色设定和价值观约束可以在不必要时砍到一句话;工具格式说明只在第一次调用工具前需要,后续完全可以交给会话记忆;few-shot 示例中真正有价值的也许只有一两条,其余都可以删掉。

但也有一条底线:安全约束和核心输出格式不能动。比如“不要在修改前删除用户未确认的文件”“代码变更后需要展示 diff 摘要”这类规则,一旦砍掉,Agent 的行为就会变得不可控。我这里说的“砍到 200 token”,不是把所有东西都删光,而是把固定长期保留的内容压缩到极致,其余全部变成临时指令,随用随发、用完即走。

3. 迁移实操:5 步把系统提示词压到 200

3.1 第一步,安装 Pi 并接上模型源

Pi 本质上是一款由某开源团队维护的终端 Agent,安装方式非常简单:一条命令拉取二进制文件,然后初始化工作目录。初始化时会让你选择模型源,我这里用的是兼容底座服务,配好环境变量之后,Pi 就能直接跑起来。

curl -sSf https://pi-agent.example.com/install.sh | bash pi init --model-source remote

pi init会生成一个配置文件,建议把配置文件单独放到项目的.pi/目录里,和代码一起提交到版本库。这样团队里其他人拉下仓库,就能直接用同一套提示词配置,不会出现各写各的混乱局面。

3.2 第二步,清空默认提示词,从零搭建最小结构

我的做法是先不看默认配置,直接把它改成空文件,然后一行一行往上加。这样做的原因是:默认配置看多了会产生“路径依赖”,总觉得哪句话都舍不得删,干脆先归零,再从实际需求出发写。

第一版我写了三个模块:

system_prompt = """ 你是终端编码助手。 每次回答前先列出将使用的命令。 代码修改后必须给出 diff 摘要。 """

这三句话加起来的 token 数连 30 都不到。换上之后我立刻跑了一个简单的“查找函数定义并解释”任务,模型可以正常工作,而且响应质量没有明显下降。关键就在于:工具调用方式、上下文填充规则、历史记录摘要这些事,并不需要放在系统提示词里教模型——Agent 框架本身会在请求拼装时自然加上。

3.3 第三步,用变量裁剪器检视每个词

空系统提示词验证通过之后,我开始做精细化修剪。这里的重点是分清楚“系统提示词”和“每轮请求的实际消耗”。Pi 配置里提供了几个变量占位符,比如{os}、{cwd}、{branch},这些变量会在每轮请求前动态替换成具体内容。如果这些内容不是每一轮都必需,把它们留在系统提示词里就是在烧钱。

我用的方法是在本地跑一个小脚本,把系统提示词里的每一行拿出来做“高频与低频”统计。具体思路是:

  • 连续 10 次对话中,某一句话都在每轮重复出现的,标记为 high-frequency;
  • 某一句话只在第一次对话时出现、之后基本不出现的,标记为 startup-only;
  • 某一句话会被变量替换成非常长的内容(比如当前仓库文件列表)的,标记为 dynamic-heavy。

对于 startup-only 和 dynamic-heavy 的内容,我直接把它们移除出系统提示词,改成在任务开始前通过一条临时指令注入。这样一个很常见的重构就发生了:原先系统提示词里写“你可以使用rg搜索代码,搜索时注意忽略 node_modules”,改成在真正需要搜索的时候,我再手动补一句“用 rg 搜索 XXX,跳过 node_modules”。

3.4 第四步,用缓存复用把 200 token 变成 0 token

在主流模型的 pricing 里,输入 token 是计费大头,尤其是那种每轮都要发送的长期提示词。但许多模型支持“前缀缓存”,意思是只要请求的开头部分和上一轮一模一样,这一部分就不再按完整费用计算,只会按缓存命中收取极低费用。

我利用的是这个特点。pi 的请求拼装是按固定页面对齐的:系统提示词会被放在第一段,紧跟其后放历史消息。只要我的系统提示词始终保持不变,并且总长度不超过缓存页的大小,后续请求就能一直命中缓存。我把提示词控制在 200 token 以内,就是为了让这部分稳定地落入缓存里。实际测试中,当会话进行到第三轮之后,系统提示词部分的输入费用基本降到了零。

注意:缓存命中的前提是提示词不能发生任何字节级变化。如果你在系统提示词里加了时间戳、随机变量,缓存就会整段失效,反而更贵。

3.5 第五步,给 Pi 挂上“瘦身巡检”

提示词又不是一劳永逸的东西——用久了总会手痒,看到模型某个回答不满意,就想在系统提示词里加一句“你回答得更详细一点”。这句话一加,200 token 变成 210 token,虽然不多,但如果在里面混进去一段几百字的“补充说明”,缓存页面可能直接翻倍。

我给自己的规矩是:系统提示词只允许在新增“输出格式”或“安全约束”时改动,其余一概写成临时指令。同时我写了一小段监控脚本,每次会话开启时把当前系统提示词长度打印出来,超过 220 token 就直接报错。这种强制克制很有效,至少把“顺手加两句话”这个坏习惯堵住了。

4. Token 账单暴降 85% 的前前后后

4.1 成本对标方法:把三次采样算清楚

要验证迁移效果,不能只看一次对话的 token 数就下结论。我把对比拆成了三个场景:

  • 场景A:修改一个函数并补充测试,交互轮次大约 6 轮;
  • 场景B:在项目中新增一个模块并运行测试,交互轮次大约 10 轮;
  • 场景C:只读任务,查找某个 Bug 的线索,交互轮次 3 轮。

每个场景分别在 Claude Code 和 Pi(配同一型号的底座模型)下跑三遍,取 token 消耗的中位数。我做的是粗略的估算,但即便如此,样本方差也不会太大,因为编码会话的特点就是固定消耗部分占大头。

4.2 真实效果:85% 是怎么算出来的

我这里取一个比较有代表性的会话来说明:修改代码并跑测试,共 8 轮交互,每次模型回复约 1800 token。

Claude Code 场景下,每轮的输入是“1.4 万系统提示词 + 以往轮次的累计历史消息 + 新的用户指令”,到了第 4 轮以后,单轮输入 token 就突破 2 万。中位数估算下来,一个 8 轮会话的总输入 token 在 12 万左右。

而 Pi 场景下,系统提示词只有 200 token 且被缓存命中,每轮追加的历史消息也更少,因为我把总结历史的操作替换成了“只保留最近两轮原始消息 + 更早内容的一句话摘要”。整体算下来,这个 8 轮会话的总输入 token 在 1.8 万左右,节省幅度刚好达到 85% 这个量级。

我把这个数据贴出来之后,群里几个朋友也做了复现。他们的结论是:会话轮次越多、系统提示词越长,节省比例越接近 90%;反之,如果你只是跑个一两轮的简单问答,节省幅度会缩水到 40% 左右。这也解释了为什么长任务、多文件重构、复杂 Bug 排查才是这种优化最受益的场景。

5. 踩坑实录:提示词砍得太狠会出人命

5.1 砍掉代码规范后,输出直接变成“自嗨”

我第一次把提示词压到 30 token 时,模型确实能干活,但风格完全放飞。它会在一个 Python 文件里混进 JavaScript 风格的驼峰命名法,还会在 commit message 里写各种情绪化文案。原因很好理解:系统提示词里关于代码风格和项目结构的指引全部被我删了,模型只能靠自身的“默认人格”去发挥。

后来我在 200 token 里强制加了一句话:“代码风格与仓库保持一致,不确定时参照旧文件。”就这一句,解决了大部分自嗨问题。它也让我意识到:系统提示词压缩不是追求绝对最短,而是在最短的前提下,保住那些模型无法从上下文中自己推断出来的关键约束。

5.2 语言提示没留,中文对话直接崩

还有个有意思的坑。我在压缩提示词的时候把“始终用中文回答”也删了,结果模型在回答技术问题时,中英文混杂得厉害,有时还会整段输出英文。如果你用英文回复倒也无所谓,但对中文用户来说,这种割裂感非常难受。

压倒性教训是:语言提示一定要保留在系统提示词中,不能放在临时指令里。因为不是每一轮你都会记得说“中文回答”,而历史消息一旦以英文为主,模型就会被带跑偏。现在我的 200 token 里固定包含这一个字段。

5.3 200 token 平时的维护方式

提示词压缩到 200 token 之后,我基本不给它留加减 Counter 的余地。只有两种情况会动它:

  • 换底座模型:不同模型对角色设定的敏感性差异很大,换模型时我会顺手清理一些针对旧模型风格的描述词;
  • 把某个频繁使用的临时指令提升为固定指令:如果我发现某条临时指令连续出现在 5 个以上会话中,才会把它写进系统提示词,同时删掉一句不那么重要的旧内容,保持总量不变。

我会维护一个“提示词版本说明”文件,记下每次删改的原因和效果。比如“V3-2:删掉工具调用格式示例,减少 110 token,理由是工具调用格式已由框架自动注入”。这个习惯帮我避免了很多“过了两周想改回旧版但毫无头绪”的尴尬。

6. 谁适合照着这份实战做迁移

如果你只是偶尔用编码助手改几行配置、问几个 API 用法,那 Claude Code 这种开箱即用的工具完全够用,省那点 token 的意义不大。但如果你和我一样,每天要在终端里开很多长会话、频繁做多文件重构、或者在一个团队里共享同一套 Agent 配置,那系统提示词从 1.4 万压到 200 带来的收益就不容忽视了。

我在实际使用中还有一个体会:token 优化这件事,本身会倒逼你把“Agent 到底哪些行为是必要的”想得更清楚。以前我默认它什么都能干,结果就是它什么都想干,连带账单也一起膨胀;现在提示词被压缩到只剩骨架,我把更多能力放在按需临时注入上,反而更容易控场。建议第一次动手的朋友不要一上来就追求极限压到 200,先给自己设一个 500 token 的中间目标,跑一周看看有没有不习惯的地方,再逐步往下收。压缩提示词是一个动态调优的过程,宁可多保留一点安全边际,也别为了省钱把 Agent 变成不听指挥的野马。

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询