同一个问题,模型这次回答正确,下次却漏了一个条件。演示时能跑通的流程,接上真实数据后,开始出现参数错误、格式异常和任务中断。
做 LLM 应用,难的往往是这些变化。用户能接受一段文案有几种写法,却很难接受同一张订单被处理两次,或产品参数在不同回答里变来变去。
原先笼统称作“模糊推理”的问题,需要拆开看:有些来自生成过程,有些是检索没有找到正确材料,还有些根本是状态管理和权限设计出了问题。把它们都归结为“模型不稳定”,就容易一直改提示词,却没有碰到故障真正发生的位置。
一、先弄清楚,输出为什么会变
生成机制不能直接当作事实校验
语言模型在生成时,会根据上下文计算后续 token 的概率,再由解码策略决定输出。Token 是模型处理文本的单位,不一定对应一个完整的字或词。
“文字接龙”可以帮助初步理解生成方式,但容易让人误以为模型只是统计某个词出现了多少次。它也不能用来证明模型没有推理能力。更需要留意的是:一段话生成得顺畅,不代表其中的事实已经核实。
对于应用开发,这个区别很实际。模型能写出带作者、年份和期刊名的参考文献,系统仍要确认文献是否存在;模型能解释一个参数,也仍要检查它是否对应当前产品版本。
因此,生成答案和验证答案,应当在设计时分别安排。
采样参数影响输出变化,但不负责判断真伪
常见的解码参数有以下几种:
| 参数 | 主要作用 | 不能据此保证什么 |
|---|---|---|
| Temperature | 调整概率分布的尖锐程度;在采样解码下,较高设置通常允许更多变化 | 低温不等于事实正确 |
| Top-K | 只保留概率最高的 K 个候选 token | 候选少不等于任务完成得好 |
| Top-P | 保留累计概率达到阈值的候选集合 | 阈值不是答案质量下限 |
这些参数是否可用、怎样组合,要看具体模型和推理接口。使用贪心解码时,某些采样参数可能不参与计算。不要把一套配置原样套到所有模型上。参数定义参考 Hugging Face 文档
即使接口允许把 Temperature 设为 0,也不宜直接承诺同一输入永远得到完全相同的输出。对重复性有要求的任务,需要在实际运行环境中测试,并记录模型、配置及输入版本。
放进上下文,不代表一定会被有效使用
《Lost in the Middle》研究发现,在所测试的模型与任务中,相关信息的位置会影响表现,放在长上下文中间的信息较难被有效利用。研究原文
这不等于所有模型都会“忘掉中间”,也不意味着长文本必然导致幻觉。它提醒我们,不要只检查输入是否超过窗口,还要检查模型能否找到真正需要的内容。
把几十份文档一次性塞进去,可能同时带入旧版本、重复段落和互相矛盾的说明。此时继续增加上下文,未必比先整理材料更有效。
二、落地时常见的十种故障
1. 答案写得完整,事实却不成立
模型可能编造日期、人物或文献,也可能把两份资料的信息拼到一起。尤其需要小心的是,错误答案往往有完整的解释,看起来并不像一次失败。
遇到这种情况,应检查关键结论的依据,而不只评价语气是否自信。没有足够材料时,让系统返回信息不足,比继续补齐细节更合适。
2. 回答用了过期信息
涉及价格、规则或产品版本时,模型已有知识未必覆盖最新情况。知识截止日期也不能简单理解为“这一天之前的所有事实都知道”。
需要更新的信息,应从当前可用的数据源获取。检索到之后,还要检查发布日期与适用范围;旧资料通过联网返回,仍然是旧资料。
3. 检索拿错了材料
问 A 产品,却找到了 B 产品的说明,问题可能出在切分、元数据过滤、查询表达、嵌入模型或排序环节。
不能仅凭模型文件大小判断检索能力,也不存在“文档超过一千份,小模型就一定失效”的统一门槛。索引与查询使用的嵌入方式应保持兼容,但向量维度相同,也不足以证明语义空间兼容。
排查时先看检索返回了什么。模型已经拿错材料,再反复要求它“认真回答”,通常解决不了上游问题。
4. 上下文里有答案,模型却没用上
这与上一种故障不同:资料可能已经找到,但夹在大量不相关内容里,或与旧说明混在一起。
可以减少无关片段、标注版本和来源、将问题需要的证据集中呈现。调整后用相同测试集比较,观察遗漏是否减少,而不是只凭输入长度判断效果。
5. 输出能读,却不能被程序使用
约定输出 JSON,结果多了一段解释;要求金额为数值,却返回了带单位的字符串。人看着问题不大,下游程序却可能无法解析。
若接口支持,可使用结构化输出约束格式,再进行类型与业务校验。即使符合 schema,字段中的事实仍可能错误,也需要处理拒绝或输出不完整等情况。结构化输出说明
6. 任务做得越久,越偏离最初目标
Agent 连续调用工具后,上下文会累积日志、临时方案和失败尝试。旧决定与新决定混在一起,容易使当前目标变得不清楚。这类退化有时被称为 context rot。
与其完整保留每一段中间对话,不如维护一份明确的任务状态:目标是什么,哪些已完成,哪些待处理,当前有哪些约束。原始记录可以另存,按需读取。
7. 工具报错之后,一直重复同一个调用
参数类型错了、必填字段缺失、目标对象不存在,都可能导致调用失败。如果系统没有区分错误原因,Agent 就可能重复提交相同请求。
工具入口应做校验,错误信息要能帮助定位问题。重试次数、时间和费用也要有上限;参数错误与临时网络故障,不应使用完全相同的恢复方式。
8. 模型说完成了,任务其实没有完成
生成了一份文件,不代表文件内容正确;写完代码,不代表测试通过。若流程只接受模型最后一句“已完成”,就可能漏掉尚未执行的步骤。
完成条件应提前定义,并尽量由可检查的结果支撑。例如文件是否存在、字段是否齐全、测试是否通过。模型的总结可以解释结果,不能替代结果。
9. 中断之后,进度无法恢复
超时或进程重启后全部重做,通常需要检查应用是否保存了任务状态,而不是把原因都归为模型没有记忆。
对于会产生外部影响的操作,还要防止重复执行。假如请求已成功,只是返回结果时断线,直接重试可能再次提交。恢复流程应先核对操作状态,必要时通过幂等设计避免重复处理。
10. 外部内容被误当成操作指令
Agent 读取网页或文件时,可能遇到要求它改变目标、泄露资料或调用工具的文字。这类内容应当作为待处理的数据,不能自动获得用户指令的权限。
防护不能只靠提示词里的“不要越权”。工具自身也要校验权限,限制可访问的数据和可执行动作。模型生成代码时,应在受控环境里运行,避免直接取得宿主系统的广泛权限。
三、分别处理提示词、参数和执行流程
提示词先把任务交代完整
目标、输入、约束和完成条件,最好分开写清楚。
例如,从合同中提取付款信息,就应明确需要哪些字段、找不到时怎样返回、日期和金额采用什么格式,以及是否需要附上原文位置。只说“准确提取”,给不了模型足够的判断依据。
禁止项也有价值,但不能代替正向要求。“不要编造”之外,还要说明材料不足时该停下来、返回空值,还是请用户补充。
重复使用的提示词,可以拆成固定规则、背景资料和本次问题。这样调整某一部分时,容易知道改动影响了什么,也方便回退到之前的版本。
关键要求可以在开头清楚列出,在末尾简短检查,但不必把同一段规则复制多遍。位置调整是否有效,需要在当前模型和任务上验证。
对于会改变操作范围、金额或权限的歧义,应先澄清。只是表达风格不够明确时,可以采用合理默认值,不必让用户回答一长串无关问题。
参数调优要保留基线
参数没有适用于全部任务的“黄金配比”。抽取类任务通常希望减少无必要的变化;创意任务可能需要探索更多表达,但两者都要保留各自的质量标准。
可以从接口支持的默认配置开始,保存基线,再一次调整一个参数。观察的也不应只有输出是否相似,还包括事实准确性、格式通过率、耗时和成本。
如果低温下错误答案反复出现,继续降低随机性没有意义。此时要回头检查输入、证据和模型能力。
模型升级后,也应重新跑一遍固定测试集。旧配置在新版本上是否仍然合适,需要结果支持。
RAG 要同时检查检索与生成
RAG 给模型提供可引用的外部资料,但并不会自动消除幻觉。它可能检索错误,也可能找到正确材料后仍然回答错误。
因此,至少要分别问两件事:相关材料有没有找回来,最终结论是否得到材料支持。把两种失败混成一个“回答准确率”,很难知道该改哪一层。
知识库还需要管理更新时间、访问权限和文档版本。测试时应包含有答案、无答案、版本冲突等情况,而不只挑能顺利回答的样例。
提示词可以要求给出来源,并在证据不足时停止作答。系统还应核对引用是否存在、引用内容是否支持结论。一个来源链接本身,并不是答案正确的保证。
长任务需要保存状态,也需要能恢复
Harness 可以理解为围绕模型运行的执行框架,负责组织上下文、调用工具、保存进度和检查结果。Anthropic 的长任务工程文章讨论了初始化、增量推进和进度记录等做法。工程文章
实际设计时,可以把任务目标、当前步骤、已完成操作和待处理问题持久化。发生中断后,先核对真实状态,再决定继续、重试还是交给人工。
错误恢复也不必全部交给模型“反思”。明确的参数错误可以由校验规则拦截,临时故障可以有限重试,状态冲突则可能需要人工判断。让模型处理它擅长的部分,同时保留常规工程措施。
多 Agent 适合拆任务,不是默认升级路线
任务可以独立分工时,让不同 Agent 处理不同材料,有助于缩小各自需要关注的范围。但它也增加了沟通、交接和结果合并的成本。
拆分之前,需要明确每个子任务的输入、输出和完成条件。多个 Agent 同时修改同一份状态,或彼此依赖对方尚未确认的结论,可能引入新的错误。
简单任务先用单 Agent 跑出基线。只有当失败记录表明分工能够解决具体问题时,再比较多 Agent 方案,而不把数量当作能力指标。
人工审核与权限控制要放在动作发生之前
涉及重要判断、敏感数据或外部写入时,可以按风险设置审核节点。审核者需要看到依据、计划执行的动作和影响范围,而不只是一个“同意”按钮。
生成代码的执行环境,应限制文件、网络和凭据访问,并设置资源预算、超时与终止条件。低 Temperature、多个 Agent 或严格格式,都不能替代这些控制。
四、不同任务,需要接受的变化不同
| 场景 | 可以保留的变化 | 必须检查的内容 | 可优先考虑的措施 |
|---|---|---|---|
| 知识问答 | 不影响事实的措辞变化 | 来源、时效、结论是否有依据 | 检索、引用核对、信息不足时停止作答 |
| 参数提取、JSON 输出 | 尽量减少字段和格式变化 | 类型、必填项、业务规则 | 结构化输出、schema 与业务校验 |
| 客服回复、文案润色 | 语气与句式变化 | 产品事实、政策、承诺范围 | 审核过的知识库与示例 |
| 创意生成 | 角度、表达和方案的多样性 | 任务限制、内容质量 | 多方案比较、人工筛选 |
| 长链路 Agent | 必要的计划调整 | 权限、状态、完成条件 | 持久化、有限重试、工具校验 |
| 高风险业务 | 按具体流程确定 | 依据、责任边界、后果 | 专业复核、权限与操作控制 |
这张表提供的是设计方向,不是通用参数配方。同样是客服回复,解释一项功能与替客户修改订单,所需控制就不同。
五、评估要能指出下一步改哪里
评估之前,先定义怎样才算完成。若一次任务只生成了草稿,还需要审核和提交,就不能把“草稿已生成”记作整个任务成功。
| 维度 | 记录什么 | 用来发现什么问题 |
|---|---|---|
| 任务成功率 | 按事先定义的条件判断是否完成 | 是否漏步骤或提前停止 |
| 准确性 | 关键事实、字段和引用是否正确 | 信息错误发生在哪一层 |
| 效率 | 总耗时、工具调用和重试次数 | 是否反复尝试无效动作 |
| 成本 | Token、API 与外部工具费用 | 单次和批量运行是否可承受 |
| 鲁棒性 | 输入改写、材料缺失、工具故障下的表现 | 是否依赖理想条件 |
| 安全性 | 越权尝试、拦截和实际影响 | 控制是否在关键动作前生效 |
| 一致性 | 同类输入多次运行的业务结果 | 波动是否影响使用 |
指标目标应由业务确定。一次头脑风暴与一次订单处理,不适合共用“成功率达到 95% 就可以上线”的门槛。一致性也未必要求逐字相同,应先说明比较的是格式、事实还是最终操作结果。
保留一套固定用例,再逐步加入真实失败样本。每次修改提示词、切分方式、模型或工具,都用同样的口径比较,尽量不要同时改变多个条件。