07 · 長跑的上下文
單輪對話裡上下文視窗是個"聊久了會忘"的問題。在 Agent 裡它變成一個結構性問題:每轉一圈,工具返回的東西就往桌上堆一層。跑到二十圈,你的目標已經被埋在最底下了。
一圈往桌上放多少東西
數一遍:
text
每一圈進上下文的:
· 它的思考("我打算搜尋……")
· 它發出的工具呼叫(工具名 + 參數)
· 工具返回的結果 ← 大頭,可能幾千字十圈就是十份工具返回。如果每份兩千字,光工具返回就是兩萬字——而你的目標只有三百字,還在最上面。
於是就有了 Agent 最典型的三種"跑著跑著變傻":
| 現象 | 原因 |
|---|---|
| 忘了目標,開始做別的 | 目標被擠到邊上或擠出去了 |
| 重複做已經做過的事 | 早期的工具返回被擠掉,它不記得查過了 |
| 早期的約束失效(開始碰不該碰的) | 約束和目標寫在一起,一起被擠掉了 |
四個辦法
一、把目標和約束放進"每輪都在"的位置
最便宜的一招。
關鍵約束不要只寫在第一條訊息裡——寫進系統提示,那是每一輪都會重新發的。
text
系統提示(每輪都在):
- 當前任務目標:【一句話】
- 完成標準:【清單】
- 硬約束:不要寫 ./data/;對外動作必須先請求確認;
連續三次同樣的嘗試無果就換路這一招幾乎零成本,但能解決大半問題。
二、讓工具返回瘦下來
03 章那條"返回要精簡",在長跑裡是硬需求:
text
❌ 讀網頁 → 返回整頁 HTML(一萬字)
✅ 讀網頁 → 返回:標題 + 正文純文本,截斷到 2000 字 + URL再進一步:讓工具返回"摘要 + 存到檔案":
text
返回:已儲存到 ./output/page-03.txt(全文 12000 字)
摘要:這是 A 家的定價頁,包含 5 個套餐,
起步價 $29/月,按席位計費。全文落到檔案裡,上下文裡只留一句摘要。 需要細節時它可以再去讀那個檔案——這就是漸進式披露在 Agent 裡的用法。
三、外接的"工作筆記"
給 Agent 一個專門的檔案當草稿本,要求它每完成一項就寫進去:
text
每查完一家,把結果追加寫入 ./output/notes.md,格式:
## A 家
- 套餐:…
- 價格:…
- 未獲得:計費單位(官網未公開,已查 pricing 和 docs 兩頁)
寫完之後,你的上下文裡不需要保留這家的原始網頁內容。好處有三個:上下文壓力降下來;你隨時能開啟這個檔案看進度;跑掛了重來時,已完成的部分還在。
四、壓縮:能用就用,但知道它的代價
有些工具會在上下文快滿時自動做一次摘要,把前面的歷史壓成一段。這能續命,但要清楚代價:
壓縮必然丟細節
被壓掉的是"當時的原文",留下的是"它對當時的總結"。如果某個細節在壓縮時被判斷為不重要,它就永遠消失了——而它的重要性可能要到第 25 圈才顯現。
所以:重要的東西別指望留在上下文裡,落到檔案裡去。(上面第三招)
拆子任務:更徹底的辦法
當一個任務實在太長,最乾淨的做法不是壓縮,是拆成幾個獨立的執行:
text
❌ 一個 Agent 跑 40 圈把三家都查完
✅ 主流程(這是一條 Workflow):
for 每一家:
起一個新的 Agent 執行,目標只有"查清這一家"
它跑完,產出寫進 notes.md
最後:彙總 notes.md好處很實在:
注意這裡發生了什麼
外層是一條 Workflow,內層每一步是一個 Agent。
這就是上一篇那句"Agent 是流水線裡的一個節點"的實際長相。 你會發現真正好用的 Agent 系統,多半長這樣——而不是一個跑八十圈的巨型 Agent。
一個判斷訊號
跑完之後,看它用了多少圈。
- 5 圈以內:很好,可能這活本來就該是 Workflow。
- 5~15 圈:正常範圍。
- 20 圈以上:警惕。多半是目標太大、或者工具返回太胖、或者它在繞圈。
- 接近你設的上限:幾乎肯定有問題,去看軌跡。
圈數是最便宜的健康指標,每次都值得瞄一眼。