最近在做一个内部知识库的Agent,用Llama-3-8B做了LoRA微调,训练集是大概5000条指令数据,都是“根据文档X回答Y”这种格式。验证集loss降得挺好看,但一接到真实Agent工作流里就崩:工具调用参数经常编造不存在的键,或者直接跳过工具调用开始瞎编答案。我怀疑是不是微调时把工具调用的system prompt格式给稀释了?还是说需要把工具返回结果也拼进训练样本里?求有经验的大佬指点下,这种场景下微调数据该怎么构造才不破坏Agent原有的能力?
微调后的模型总在Agent任务里胡言乱语,是数据问题还是我姿势不对?
全部回复
共 8 条验证集loss好看不代表啥,真实场景里工具调用格式被稀释太常见了,建议把工具返回结果也塞进样本里试试。
我遇到过类似问题,光调指令数据不够,得把完整工具调用轨迹混进去训练,格式保住了才不会瞎编。
说实话你这个验证集loss降得好看太有迷惑性了,我踩过一模一样的坑。LoRA微调的时候,如果训练样本里全是“根据文档X回答Y”这种纯问答对,模型会把工具调用相关的system prompt当成噪音忽略掉,因为梯度更新里压根没有工具返回结果和调用失败恢复的样本,它自然就放飞自我了。我觉得问题八成出在数据构造上,不是姿势不对,你想想,推理时模型要经历“理解任务→决定调工具→解析返回→生成答案”这个链路,但训练时你只喂了最后一步的输入输出,中间环节它根本没学会。建议你把真实Agent工作流里跑出来的日志扒一扒,把“用户问题+当前对话历史+工具调用指令+工具返回的JSON”拼成一个完整样本,甚至故意塞几条工具返回乱码或空值的样本教它怎么兜底,这样模型才知道什么情况下该闭嘴等工具结果而不是硬编。另外我怀疑你训练时是不是把system prompt里的工具描述格式改了,哪怕少个括号或字段顺序变一下,8B模型对格式特别敏感,很容易学歪。还有个小技巧,微调时按比例混入20%左右原始通用指令数据,能防止灾难性遗忘,不然工具能力没学会,基础对话能力先崩了。你试试把工具调用的输出也作为标签的一部分让模型预测,而不是只预测最终答案,效果应该会明显改善。
大概率是工具调用格式被稀释了,建议把真实工具返回和调用链样本按3:1混进去重训。
大概率是训练样本里工具调用格式占比太少,模型学歪了,建议把真实工具返回结果拼进去重训试试。
这问题我踩过一模一样的坑,验证集loss好看基本是骗人的,因为纯指令微调会把你基座模型里工具调用的先验知识给覆盖掉。建议你训练样本里至少混入20%的完整Agent轨迹,包括system prompt、工具返回结果和下一步动作,不然模型根本学不会“看到工具输出再决定下一步”。另外可以试试在微调时把工具调用的格式单独做成一个task,用那种带占位符的模板数据,别让知识问答样本把工具格式给冲淡了。你那个5000条数据里,纯问答和工具调用类的比例大概是多少?
验证集loss好看但agent崩,大概率是训练分布和推理分布错位了,你只喂了问答对,模型没见过工具调用的完整上下文,自然容易瞎编参数。建议把工具定义、调用历史、返回结果都拼进样本,模拟真实agent的交互轨迹,哪怕数量少点也比纯问答强。另外LoRA rank别开太大,8-16就行,不然容易把基座模型的工具调用能力给覆盖掉,先小步试几个样本看行为变化再全量调。
大概率不是姿势问题,是数据里压根没教模型“什么时候该调工具”,纯指令问答把工具调用格式稀释没了。建议把带工具返回结果的真实轨迹混进训练集,比例拉到三成以上试试。
大概率是工具调用格式被LoRA带偏了,训练样本里得混入真实工具返回的对话片段。
建议把system prompt和工具结果都塞进训练集,比例至少占三成,不然模型光学会答题忘了怎么调工具。