编写代码很少是一个线性的过程。你写一个函数,运行它,看到错误信息,盯着屏幕,然后进行迭代。这个循环——编码、执行、分析反馈并进行迭代——是软件开发的核心。
然而,大型语言模型 (LLM) 历史上一直难以应对这个循环。虽然它们在“一次性代码生成” (一次性编写出解决方案) 方面表现出色,但在修复自身错误方面却臭名昭著。当 LLM 生成有缺陷的代码时,仅仅将错误信息粘贴回提示词中,往往会导致“死亡螺旋”,即模型在错误上加倍下注,或引入新的 Bug。事实上,先前的研究表明,要求模型从头开始生成一个全新的解决方案 (独立采样) ,往往比要求它修复前一个方案更有效。
这把我们要带到了 Meta AI 的一篇新论文: “RLEF: Grounding Code LLMs in Execution Feedback with Reinforcement Learning” (RLEF: 通过强化学习将代码 LLM 落地于执行反馈) 。
研究人员提出了一种方法,教导模型如何真正利用编译器反馈和测试结果来改进其代码。通过使用强化学习 (RL) 进行端到端的模型训练,他们在竞技编程基准测试中取得了最先进的结果,大幅降低了寻找正确解决方案所需的计算成本。
在这篇文章中,我们将剖析 RLEF 方法,探索训练循环背后的架构,并分析为什么这种方法标志着从提示工程 (Prompt Engineering) 到真正的模型落地 (Grounding) 的重大转变。
问题所在: 产生幻觉的解决方案 vs. 有依据的调试
为了理解为什么 RLEF 是必要的,我们必须先看看今天通常是如何构建用于编程的“AI 智能体”的。
现状: 提示工程与脚手架
目前最先进的编程系统 (如 AlphaCodium 或 MapCoder) 依赖于繁重的“脚手架”。这涉及一个复杂的、预先编程的工作流,其中 LLM 被提示去:
- 生成计划。
- 生成代码。
- 生成测试。
- 运行代码。
- 如果失败,使用特定的提示模板请求修复。
虽然有效,但这些系统很脆弱。它们依赖于冻结的基座模型 (如 GPT-4) 的固有能力。如果模型没有经过明确训练来解释特定类型的堆栈跟踪或逻辑错误,再巧妙的提示也无法让它成为调试大师。此外,这些系统十分昂贵。它们通常需要采样数十甚至数百个解决方案才能找到一个可行的 (这一指标被称为 pass@k,其中 k 是采样预算) 。
目标: 高效的自我修复
RLEF 的作者认为,任何提供自然语言界面的决策智能体都必须具备两项特定技能:
- 指令遵循: 推断用户的意图 (标准的 LLM 擅长此道) 。
- 基于反馈确立依据 (Grounding in Feedback) : 利用中间结果 (如错误信息) 来指导下一步行动。
这篇论文的目标是摆脱复杂的人工脚手架,转而对模型进行微调,使其天生擅长迭代调试循环。
RLEF 方法
这篇论文的核心贡献是一个名为 Reinforcement Learning with Execution Feedback (RLEF) (基于执行反馈的强化学习) 的框架。他们不是仅仅训练模型预测正确代码片段中的下一个 Token (标准的监督微调) ,而是训练模型驾驭一个多轮对话,在对话中它会接收来自编译器的反馈。
1. 迭代环境
研究人员不将代码合成视为翻译任务 (文本到代码) ,而是将其视为马尔可夫决策过程 (MDP) ——一系列的决策和状态。
环境的工作原理如下:
- 观察 (\(o_0\)): 模型接收自然语言的问题描述。
- 动作 (\(a_0\)): 模型生成代码解决方案。
- 执行: 代码在一组 公开测试 (Public Tests) 上运行。
- 反馈: 如果代码失败,错误信息 (stderr、堆栈跟踪或失败的测试用例信息) 会被格式化为文本,并作为新的观察反馈给模型。
- 循环: 模型生成改进后的解决方案 (\(a_1\))。

如上图 2 所示,这个过程创建了一个对话历史。左侧展示了流程: 模型提出代码,环境 (沙盒) 运行它,反馈循环回传。右侧展示了一个具体示例。模型编写了一个太慢的解决方案 (超出时间限制) 。反馈明确指出了这一点。模型随后“意识”到它需要更高效的方法 (使用缓存) 并重写了代码。
2. 测试集拆分: 公开 vs. 私有
该方法中一个关键细节是测试用例的分离。
- 公开测试: 对智能体可见。对话过程中提供的反馈仅来自这些测试。
- 私有测试: 这是留出的测试,智能体在剧集 (Episode) 期间从未看到过其反馈。
为什么这很重要?如果模型收到了所有测试的反馈,它可能会学会“作弊”,通过硬编码边缘情况来满足特定输入,而没有真正解决算法的通用逻辑。通过仅在最后通过私有测试时才奖励模型,研究人员确保模型学习的是鲁棒的通用解决方案。
3. 强化学习设置 (PPO)
作者使用了 近端策略优化 (PPO) , 这是 RLHF (基于人类反馈的强化学习) 的标准算法,但在这里针对执行反馈进行了调整。
训练过程涉及两个模型:
- 策略模型 (\(\pi\)): 正在被训练生成代码的 LLM。
- 价值模型 (\(V\)): 一个预测当前对话状态有多大可能导致正确解决方案的模型。
奖励函数
奖励信号是任何 RL 系统中最关键的组件。在 RLEF 中,奖励是稀疏的——意味着模型主要仅在对话的最末尾获得信号。
奖励函数 \(R(s_t, a_t)\) 定义如下:

让我们分解这个公式:
- 成功 (+1): 只有在剧集结束时,代码通过了所有测试 (公开和私有) ,模型才会获得 +1 的奖励。
- 失败 (-1): 如果在剧集结束时有任何测试失败,它将获得 -1。
- 无效代码惩罚 (-0.2): 如果模型在中间步骤生成的甚至不是有效的 Python 代码 (胡言乱语) ,它会受到轻微的惩罚。这防止模型浪费轮次。
- KL 惩罚 (\(\beta \dots\)): 这是 RL 训练中的标准项,防止模型偏离其原始训练分布 (“参考模型” \(\rho\)) 太远。它确保模型不会为了利用奖励指标作弊而开始输出奇怪的文本。
“轮次级”价值函数
标准的 PPO 通常训练价值函数来预测每一个 Token 的价值。然而,在编程中,特定的 Token (如 def 或 import) 本身没有内在价值;价值来自于完整的程序。
研究人员使用了一种混合方法:
- 策略: 在 Token 级别 上优化 (LLM 的标准做法) 。
- 价值函数: 基于提示词 (Prompt) 的最后一个 Token 预测 整个轮次 的价值。
- 优势 (Advantage) : “优势” (即动作比预期好多少) 针对每个回复计算一次,并应用于该回复中的所有 Token。
这实际上是在告诉模型: “你刚刚写的这一整块代码导致了成功,所以让组成它的所有 Token 出现的概率更高。”
实验与结果
该团队在 CodeContests 上对其方法进行了基准测试,这是一个具有挑战性的竞技编程问题数据集 (类似于 LeetCode Hard 或 Codeforces) 。这些问题比 HumanEval 等标准基准测试要难得多。
他们使用 Llama 3.1 (8B 和 70B 参数) 作为基座模型。
最先进的性能
结果令人印象深刻。RLEF 使模型能够超越以前最先进的系统,同时使用的推理预算仅仅是后者的一小部分。

查看上面的 表 1 , 我们可以看到几个关键的对比:
- 采样效率: 指标
1@3意味着“在 3 次尝试内找到一个正确的解决方案”。经过 RLEF 训练的 Llama 3.1 70B 模型在验证集上达到了 37.5% 的解决率,击败了庞大的 AlphaCode 2 估算值 (使用更少的样本) ,并碾压了 AlphaCodium (使用 GPT-4) 。 - 巨大的提升: 8B 模型的性能从 4.1% (基座 instruct) 跃升至 12.5% (RLEF) 。70B 模型从 25.9% 跃升至 37.5% 。
- 击败 GPT-4 脚手架: RLEF 70B 模型 (1@3) 优于使用 GPT-4-Turbo 的 MapCoder (1@19)。这证明了一个经过专门微调的开放权重模型可以击败依赖提示工程的庞大专有模型。
效率与扩展
RLEF 最具说服力的论据之一是推理效率。许多智能体框架需要数百次调用 LLM 才能解决一个难题。RLEF 被设计为在小预算下工作 (例如 3 个轮次) 。

图 1 展示了解决率与采样预算 (k) 的关系。
- 橙色线 (70B + RLEF) 远高于 GPT-4 和 AlphaCodium 的数据点 (星号和圆圈) 。
- 即使在低预算下 (X 轴左侧) ,RLEF 仍保持高性能。这意味着模型不仅仅是在“猜测”更多;它是在更聪明地猜测。
模型真的在“调试”吗?
怀疑论者可能会问: 模型是真的利用反馈来修复代码,还是仅仅采样了一组多样化的随机解决方案并碰巧成功了?
为了测试这一点,作者分析了“编辑距离” (代码改变了多少) 和修复的成功率。

图 3 对模型的行为提供了迷人的观察:
- 错误减少 (左上) : 与基座模型 (蓝色条) 相比,RLEF 模型 (橙色条) 在第 2 轮和第 3 轮的错误数量 (输出错误、异常、超时) 显著下降。
- 代码变更 (右上) : “chrF” 图表衡量了连续代码生成之间的相似性。
- 蓝色条 (基座模型) 聚集在 1.0 附近,意味着基座模型经常忽略反馈并再次输出完全相同的代码。
- 橙色条 (RLEF) 显示了变化的分布。模型正在积极重写代码部分以解决错误。
“随机反馈”消融实验
关于落地能力的最终证据来自于一项消融研究,研究人员向模型提供了 随机反馈——来自完全不相关问题的虚假错误信息。
如果模型只是忽略反馈并进行猜测,那么随机反馈应该不会对它造成太大伤害。

如 图 4(a) 所示:
- 实线 (真实反馈) : 随着模型被允许更多轮次 (从 2 到 10) ,性能提升。它收敛于正确的解决方案。
- 虚线 (随机反馈) : 性能持平或下降。模型试图“修复”不存在的 Bug,从而破坏了自己原本有效的逻辑。
这证实了 RLEF 生成的模型会密切关注它们收到的具体错误信息。
结论与启示
RLEF 论文展示了我们构建编程智能体方式的一个关键转变。我们不再将 LLM 视为需要通过复杂的提示链来诱导工作的静态文本生成器,而是可以将它们视为 可学习的智能体 。
通过在训练期间——而不仅仅是推理期间——将模型暴露在执行环境中,模型内化了编程的动态过程。它学会了 TimeoutError (超时错误) 需要算法上的改变 (如添加缓存) ,而 SyntaxError (语法错误) 则需要表面层面的修复。
主要收获:
- 训练 > 提示: 基于执行反馈的强化学习微调,比使用卓越基座模型 (GPT-4) 的复杂提示工程产生更好的结果。
- 采样效率: RLEF 允许模型用更少的生成次数解决问题,降低了 AI 编程助手的成本和延迟。
- 真正的落地: 模型真正学会了利用错误信息,这一点通过它们在面对虚假反馈时的失败得到了证明。
对于学生和研究人员来说,RLEF 凸显了超越“下一个 Token 预测”损失函数的潜力。当我们专门针对结果 (通过测试) 而不是过程 (模仿人类文本) 进行优化时,我们解锁了模仿真实推理和自我纠正的能力。随着执行环境越来越多地整合到 LLM 训练管道中,我们可以期待 AI 智能体不仅成为代码的编写者,更将成为称职的维护者和调试者。
](https://deep-paper.org/en/paper/2410.02089/images/cover.png)