别被 1M 上下文给骗了,大模型产生幻觉的真相其实是内存溢出
简单来说,上下文窗口就是模型的“短期记忆力”或“办公桌面”。无论模型宣称支持多少 token,它的处理能力并不是均匀分布的。当对话长度逼近上限,或者由于 Token 计数机制导致早期的指令被挤出窗口时,模型面对缺失的信息,为了维持对话的流畅度,会启动概率预测来填充空白,这就是典型的“一本正经地胡说八道”。
在实际开发中,这种失效最典型的场景就是“指令丢失”。举个例子,如果你在 Session 开始时明确要求:“所有代码必须兼容 Python 3.9,且严禁使用任何第三方库”,在对话的前 10 轮里,它表现得非常克制。但随着对话轮数增加,历史记录占用的 token 越来越多,早期的约束指令就像掉下桌子的纸片一样,被模型彻底“遗忘”了。这时候你再让它写个网络请求,它可能会毫无压力地甩给你一段依赖 requests 库的代码。这并不是模型不听话,而是之前的约束已经滚出了它的可见窗口。
更反直觉的是一个名为“Lost in the Middle”(中间丢失)的现象。很多模型号称支持 128K 甚至 1M 的超长上下文,但实验证明,模型对输入文本的开头和结尾记忆最深,而夹在中间的内容最容易被忽略。如果你喂给它一份 50 页的 PDF 合同,然后询问第 27 页某个具体的条款细节,模型很可能会自信地编造一个听起来极其合理的答案,因为它在检索中间段落时出现了失效。
除了物理空间的限制,很多 AI 框架在底层处理长文本时会采用“总结截断”策略。当检测到历史记录过长时,系统会自动将之前的对话压缩成简短的摘要。比如,你之前定义了一个极其复杂的函数 calculate_tax_refund_v2(income, region, year),在被总结后,历史记录里可能只剩下一句“用户定义了一个计算退税的辅助函数”。当你后续要求它重构这段代码时,模型由于丢失了原始的参数定义,只能靠猜来补全,结果就是满屏的 NameError 或逻辑 Bug。
此外,在处理多文档分析时,大窗口反而可能成为陷阱。当你一次性往窗口里塞 10 份相似的 API 文档(比如 v1.0 到 v1.9 的迭代版本),模型很容易将 A 文档的字段名和 B 文档的逻辑流程缝合在一起,造出一个现实中根本不存在的“混合版”接口。
对于开发者而言,单纯追求大窗口是没有意义的。在构建 AI Agent 或复杂工作流时,不能寄希望于模型能像人类一样完美记住所有细节。更高效的策略是在关键节点手动重复核心约束,或者采用 RAG(检索增强生成)通过向量数据库精确检索片段,而不是把整个文档库直接粗暴地塞进上下文窗口。