这道题其实问的是,怎么在对话系统里把闲聊和功能调用分清楚,避免模型动不动就瞎调工具。我理解核心就一句话:意图边界模糊,需要在能调工具和该调工具之间,建好几道过滤。
先说模型设计层。一个直接的做法是加一个显式的意图分类器,在触发 [[Function Calling]] 之前先分一下,输出 chat、tool_call 或者 uncertain 三档。这个分类器可以用轻量模型,比如 BERT 级别,或者用 [[LoRA]] 微调一下,负担不大。另一个思路是双模型架构,一个路由模型专门判断该不该走工具分支,另一个执行模型专心做工具调用,这样两个模型各管一摊,闲聊数据不会干扰工具模型。训练的时候,我会在 [[SFT]] 阶段刻意加一些负例,就是那些明显是闲聊的样本,明确标出来 tool_calls 为空。[[RLHF]] 阶段也可以引入惩罚,用户说“我没让你查这个”就是一个很强的负向信号。
再一个就是提示工程。我会在 [[System Prompt]] 里把边界定义写清楚,比如“只有用户明确请求执行任务时才调用工具,泛泛而谈、情绪表达、假设性讨论都不调”。然后加几个 [[Few-shot]] 示例,正例是“查北京明天天气”调天气工具,负例是“今天天气真差”就回一句“是啊,适合宅家”。还可以加一步强制反思,用 [[Chain-of-Verification]] 的思路,让模型先自问“用户是在请求我执行操作吗?”,再决定要不要调工具。
后处理策略这块也很关键。我会设一个置信度阈值,比如工具选择概率低于 0.7 就降级成闲聊回复。再一个是参数完整性校验,如果必填参数缺失,先问清楚而不是强行调用。上下文一致性检查也很有用,比如用户连续聊了三轮闲话,突然蹦出一个工具调用,那就触发一个确认话术“您是想查……吗?”。用户反馈闭环也得有,提供一个“这不是我要的”按钮,实时修正路由策略。
这里有个重要的取舍:宁可漏调,不可错调。闲聊误调工具的伤害,远大于功能没识别出来,没识别可以追问澄清,误调会让用户觉得系统很蠢。所以我会把后处理做得保守一些,高模糊场景用“您是指……吗?”过渡,不直接执行。
还有一个点值得注意,就是多轮对话里的意图漂移。用户可能前几轮在闲聊,突然切到功能请求,这时候模型容易受上下文干扰。我倾向于引入一个轻量的状态机,维护一个“当前意图状态”,结合[[滑动窗口]]判断意图是否发生了切换,而不是单纯依赖单轮分类。
所以说,我会把整件事看成一条流水线,从模型到提示到后处理,每层都做一点过滤,最终目标是让工具调用既准又稳。