生成时间:2026-04-06

Embarrassingly Simple Self-Distillation Improves Code Generation

论文链接:arXiv:2604.01193

一句话总结:这篇论文提出了一种极其简单的自蒸馏方法 SSD(Simple Self-Distillation):不需要外部教师模型、不需要执行验证、不需要强化学习,只用模型自己采样出来的代码继续做一轮普通 SFT,就能显著提升代码生成性能,尤其是在中高难度题目上。

1. 这篇论文在讲什么?

作者想回答一个非常直接的问题:代码大模型的后训练,是否一定要依赖高质量标注、单元测试验证、拒绝采样、RL 或者更强教师模型?他们的答案是:不一定。有时候,只要让模型用合适的采样策略生成一些自己的答案,再把这些答案反过来当作监督数据继续训练,模型就能明显变强。

这个结论之所以重要,是因为它挑战了一个常见直觉:很多人默认“错误样本没价值”或者“没有 correctness signal 的数据没法学到东西”。而这篇论文展示出,即便不判断答案是否正确,模型依然可以从这些样本中学到一种更适合代码生成的概率分布结构。

2. 方法为什么叫“Embarrassingly Simple”?

因为流程简单得几乎让人不好意思:

  1. 准备一批代码题 prompt;
  2. 用当前模型自己生成一批答案;
  3. 不做执行验证,不看是否通过测试;
  4. 把这些 (prompt, answer) 对直接拿去继续做 SFT;
  5. 得到一个更强的代码模型。

整个过程不需要 reward model,不需要 PPO/GRPO,不需要 verifier,不需要 rejection sampling,也不需要一个更大的 teacher model。作者把这种方式称为 Simple Self-Distillation(SSD)

3. 论文的核心洞见:代码生成里存在 Locks 和 Forks

作者认为,代码生成的难点之一不只是“知识够不够”,而是模型在不同 token 位置上需要的行为完全不同。

问题在于:传统的解码通常使用全局统一的 temperature / top-p / top-k,无法同时满足 Locks 所需的高精度和 Forks 所需的高探索。作者认为,SSD 的价值就在于它不是只改“解码器读法”,而是在训练后真正重塑了模型内部的 token 概率分布。

4. SSD 具体怎么做?

论文中 SSD 的关键不是“随便采样”,而是使用一组有设计感的采样策略来生成训练数据:训练数据生成阶段采用偏高温度,同时配合 top-k / top-p 截断;每个 prompt 只采样 1 条答案;几乎不做过滤,只去掉极端无效输出。然后对这些数据做最普通的自回归交叉熵训练,也就是标准 SFT。

这个设计背后的直觉是:高温度可以让模型在 Forks 位置多探索一些可能路线;top-k / top-p 截断可以防止长尾垃圾 token 太多,避免生成彻底失控;最终得到的是一批“带探索、但不过分发散”的样本;模型在这些样本上继续训练后,会逐渐学出一种更适合代码生成的内部概率结构。

5. 为什么这种方法有效?

作者给出的解释不是“模型从自己的答案里学到了大量新知识”,而是:SSD 本质上在做分布重塑(distribution reshaping)

论文把这种作用大体拆成两层:一是 Support Compression,由于训练数据来自截断后的采样,模型会把概率质量更集中到合理候选集里,减少长尾噪声,这会让 Locks 更稳定;二是 Within-support Reshaping,由于采样时用了更高温度,合理候选之间的概率差会被拉平一些,因此模型不会在 Forks 位置过早塌缩到单一路线,这会让探索更充分。

组合起来的效果就是:该准的时候更准,该发散的时候更愿意发散。这也是为什么 SSD 能同时提升 pass@1 和 pass@5,而不是单纯把模型变得更保守。

6. 实验设置

论文使用了多个模型和基准,覆盖 instruct 模型和 thinking 模型,包括 Llama-3.1-8B-Instruct、Qwen3-4B-Instruct、Qwen3-4B-Thinking、Qwen3-30B-Instruct、Qwen3-30B-Thinking。训练数据大约是 1 万条竞技编程 prompt。评测重点使用 LiveCodeBench v6,并关注 pass@1、pass@5 以及不同难度(easy / medium / hard)上的表现变化。

7. 最重要的实验结果

这组结果说明 SSD 的作用不是让模型只会更保守地吐一个最可能答案,而是让它更容易覆盖“多个可能正确的解空间”。

8. 一个非常反直觉的实验:烂数据也有用

作者做了一个特别有冲击力的 stress test:故意用非常高的 temperature、几乎不做截断,让模型生成质量很差的样本,其中很多代码甚至都不可执行,部分输出接近乱码。按常识看,这种数据拿去继续做 SFT 应该会污染模型;但实验发现,模型性能仍然能提升。以 Qwen3-30B-Instruct 为例,pass@1 依然能从 42.4% 提升到 48.1%。

这说明 SSD 的收益主要不是来自“模型看到了更多正确代码”,而是来自训练过程对 logits 结构的重塑。也就是说,即使训练样本本身不算高质量,只要它们携带了某种合适的分布信号,模型也可能从中获益。

9. 为什么单纯调解码参数不够?

论文专门比较了这件事,发现:只做 decode-only 调参,收益很有限,远远不如 SSD。作者认为原因在于:单纯调解码参数,只是在“读取”原模型已有分布;SSD 则是在训练后真正改变了模型内部的概率几何;因此 SSD 不是一个 sampling trick,而是一个参数级别的后训练方法。

这点非常关键,它说明这项工作不是在卖一个“更好的解码超参”,而是在强调:后训练可以通过重塑分布结构来释放模型已有潜力

10. 这篇论文对实践者有什么启发?

11. 局限性

12. 我的理解:这篇论文为什么值得看?

模型性能的瓶颈,不一定只是知识不足,也可能是分布结构不对。

很多代码题模型“做不出来”,未必是因为它不知道怎么做,而可能是:在关键 token 上不够坚定;在策略分叉点上又过于保守;最后把本来有能力解对的问题,在生成过程中解坏了。

SSD 提供的就是一种极低成本的分布再塑形方法。它不像 RL 那样复杂,也不像 rejection sampling 那样依赖外部执行环境,却能实实在在地释放已有能力。这使它非常适合作为代码后训练中的强 baseline,甚至可能成为很多更复杂方法之前的默认第一步。

13. 结论

在代码生成中,模型可以仅通过学习自己“经过温度和截断采样后的原始输出”,而无需任何正确性反馈,就显著提升性能。

这说明:高质量标签当然重要,但并不是唯一道路;有时候,一个设计得当的采样分布,本身就是非常强的训练信号。