☰
smol-course 偏好数据集生成实战:用 distilabel 构建 DPO 训练数据流水线
2026/10/9 1:56:03 网站建设 项目流程
  • 教程
  • 人工智能
  • 大模型
  • NLP
  • 微调

【免费下载链接】smol-course

A course on aligning smol models.

项目地址:https://gitcode.com/gh_mirrors/smo/smol-course
点击查看免费下载

本文以 Hugging Face smol-course 第六单元《合成数据集》中的偏好数据集章节(units/vi/unit6/3.md)为骨架,系统讲解如何为 DPO 等偏好对齐方法生成高质量偏好数据集。你将掌握模型池化(Model Pooling)与 EvolQuality 两种补充回答(completion)的方法,学会使用 UltraFeedback 为回答打分并生成评语、从而判定chosen与rejected偏好对,并能在 distilabel 流水线中直接落地运行。

从指令数据集到偏好数据集:偏好从哪来

在偏好对齐章节中,我们学习过直接偏好优化(Direct Preference Optimization)。要训练这类方法,前提是拥有一份"偏好数据集":对同一条instruction,模型需要看到多个completion,并明确其中哪个更优(chosen)、哪个更差(rejected)。只有存在清晰、无歧义的偏好信号,模型才能被正确地优化。

合成数据集模块将 LLM 合成数据划分为三大类:指令(instructions)、偏好(preferences)与评语(critiques)。本文聚焦第二类,并在过程中自然用到第三类技术——用模型的评语与改写来提升既有数据质量。上一节《生成指令数据集》(对应英文版 instruction_datasets.md)已介绍过 basic prompting、SelfInstruct、EvolInstruct、Magpie 等方法;偏好数据集正是在这些方法产出的指令数据之上,进一步为每条 instruction 补充多个 completion 并给出排序依据。

构造偏好数据有一个关键约束:第二条 completion 不能与第一条在整体质量和措辞上过于相似。原因在于,如果两个回答几乎一样,模型就无法学到明确的偏好方向。至于如何判定chosen与rejected,将在生成分数一节详细展开。

生成多个回答(completions)

为同一条指令补充多个 completion,最直接的方式就是提示(prompt)一个模型去生成。本章介绍两条主流路径:用不同模型"池化"出第二条回答,或用 EvolQuality 把已有回答"演化"成更优版本。

模型池化(Model Pooling)

模型池化即使用不同模型家族的模型来生成第二条 completion。要进一步提升第二条 completion 的质量与多样性,还可以:

  • 调整生成参数(generation arguments),例如调高temperature;
  • 使用不同的 prompt 模板或 system prompt,让第二条回答体现模板中定义的特定特征;
  • 理论上,可以取两个质量不同的模型,把质量更好的回答直接作为chosen。

下面的流水线加载HuggingFaceTB/SmolLM2-1.7B-Instruct与Qwen/Qwen2.5-1.5B-Instruct两个模型,通过distilabel的transformers集成为同一条 instruction 生成两个合成回答:

from distilabel.llms import TransformersLLM from distilabel.pipeline import Pipeline from distilabel.steps import GroupColumns, LoadDataFromDicts from distilabel.steps.tasks import TextGeneration with Pipeline() as pipeline: data = LoadDataFromDicts(data=[{"instruction": "什么是合成数据?"}]) llm_a = TransformersLLM(model="HuggingFaceTB/SmolLM2-1.7B-Instruct") gen_a = TextGeneration(llm=llm_a) llm_b = TransformersLLM(model="Qwen/Qwen2.5-1.5B-Instruct") gen_b = TextGeneration(llm=llm_b) group = GroupColumns(columns=["generation"]) data >> [gen_a, gen_b] >> group if __name__ == "__main__": distiset = pipeline.run() print(distiset["default"]["train"]["grouped_generation"][0]) # {[ # '合成数据是人为生成的、模拟真实世界使用的数据。', # '合成数据指的是以人为方式生成的数据。' # ]}

这段代码的关键点:

  • 流水线由LoadDataFromDicts(加载数据)、两个TextGeneration步骤(并行生成)、GroupColumns(合并结果)组成;
  • data >> [gen_a, gen_b] >> group中,>>表示数据流向,[]表示前一步的输出同时作为列表中两个步骤的输入,即两条生成分支并行执行;
  • GroupColumns(columns=["generation"])按列合并两个分支的输出,得到grouped_generation列,每个元素是同一 instruction 的两个 completion。

同样的流水线也出现在练习 Notebook中,那里还示范了如何用distiset.push_to_hub(...)把结果推送到 Hub。此外,distilabel 的Pipeline会自动缓存生成结果、内置容错(生成步骤失败时流水线继续运行)、并行执行所有生成步骤,还可用draw方法可视化数据流——这些特性在指令数据集一节中有更完整的说明。

EvolQuality:演化回答质量

EvolQuality 与指令数据集一节中的 EvolInstruct 类似,但区别在于:它演化的是completion而不是输入prompt。任务同时接收prompt与completion,基于一组标准把 completion 改写为对该 prompt 更好的版本。这些标准围绕提升有用性(helpfulness)、相关性(relevance)、深度(deepening)、创造性(creativity)或细节(details)展开。由于它能自动生成第二条回答,因此可以直接用于扩充偏好数据集;理论上甚至可以假定演化结果优于原始回答,将其直接作为chosen。

该 prompt 在 distilabel 中实现于evol_quality任务目录,简化版如下:

我想让你扮演一名回复改写者(Response Rewriter)。 给定一个 prompt 和一个回复,请将回复改写为更好的版本。 根据以下标准使 prompt 复杂化: {{ criteria }} # Prompt {{ input }} # 回复 {{ output }} # 改进后的回复

使用EvolQuality类(num_evolutions=1,即只演化一代):

from distilabel.llms import TransformersLLM from distilabel.steps.tasks import EvolQuality llm = TransformersLLM(model="HuggingFaceTB/SmolLM2-1.7B-Instruct") evol_quality = EvolQuality(llm=llm, num_evolutions=1) evol_quality.load() instruction = "什么是合成数据?" completion = "合成数据是人为生成的、模拟真实世界使用的数据。" next(evol_quality.process([{ "instruction": instruction, "response": completion }])) # 通过手工提示生成合成数据的过程,涉及创建模拟真实世界使用模式的人工数据集。

演化后的回答更复杂、也更贴合 instruction。但正如 EvolInstruct 一节所提醒的:演化是把双刃剑,演进结果不一定总是更好,因此必须配合下一节的评估技术来保证数据集质量。这一整套"生成回答 → 演化 → 打分"的流程,正是英文版文档 preference_datasets.md 所描述的标准做法。

生成分数

分数衡量一条回答相对另一条被偏好的程度,一般可分为绝对、主观与相对三类;本课程聚焦前两类,因为它们对构造偏好数据集最有价值。用 LLM 打分与写评语的方式,与评估章节中介绍的技术有重叠;和多数评估技术一样,打分与评语通常需要更大的模型,才能更好地与人类偏好对齐。

UltraFeedback

UltraFeedback 针对给定prompt及其completion生成分数(score)与评语(critique),其要点如下:

  • 分数基于一组标准衡量 completion 的质量。细粒度标准有四项:helpfulness(有用性)、relevance(相关性)、deepening(深度)、creativity(创造性)。这些标准很有用,但通常从整体(overall)标准入手更简单,也能简化打分流程。
  • 分数可直接用于判定哪个 completion 是chosen、哪个是rejected。由于分数是绝对的,它还能作为有趣的离群值过滤器:找出最差的回答,或差异过大/过小的偏好对。
  • 评语为分数提供理由,可作为额外上下文帮助我们理解分数差异。LLM 能生成详尽的评语,这很有用,但也会引入额外成本与复杂度——生成评语远比生成代表分数的单个 token 昂贵。

该 prompt 在 distilabel 中实现于ultrafeedback模板目录,简化版如下:

根据各种标准评估模型输出:有用性、相关性、深度、创造性 你的角色是基于上述因素提供整体评估。 按 1 到 5 分对输出的整体质量打分。 请按以下格式作答:分数 - 理由 # 输入 {{ input }} # 回复 {{ output }} # 分数 - 理由

使用UltraFeedback类对模型池化得到的两个 completion 打分:

from distilabel.llms import TransformersLLM from distilabel.steps.tasks import UltraFeedback llm = TransformersLLM(model="HuggingFaceTB/SmolLM2-1.7B-Instruct") ultrafeedback = UltraFeedback(llm=llm) ultrafeedback.load() instruction = "什么是合成数据?" completion_a = "合成数据是人为生成的、模拟真实世界使用的数据。" completion_b = "合成数据指的是以人为方式生成的数据。" next(ultrafeedback.process([{ "instruction": instruction, "generations": [completion_a, completion_b] }])) # [ # { # 'ratings': [4, 5], # 'rationales': ['可以更具体', '定义很好'], # } # ]

注意输入字段是generations(回答列表),输出为ratings(每项 1–5 分)与rationales(评语)。得到两个分数后,把分数更高者标记为chosen、更低者标记为rejected,即可形成 DPO 训练所需的偏好对。

最佳实践

  • 整体分数更划算:整体(overall)分数比针对性评语与细分标准分数更便宜、更容易生成;
  • 用更大的模型打分与写评语,以更好地对齐人类偏好;
  • 使用多样化的模型集合来生成分数与评语,避免单一模型的系统性偏差;
  • 持续迭代system_prompt与模型的配置,直至数据质量稳定。

动手实践:练习 Notebook

《创建偏好对齐数据集》练习 Notebook 给出了一个最小可运行流水线(即模型池化部分),并提供三个递进难度的练习目标:

  • 🐢 生成一个偏好对齐数据集;
  • 🐕 在偏好数据集生成中加入回答演化(response evolution);
  • 🦁 在回答演化基础上再叠加模型池化(model pooling)。

Notebook 环境准备与运行要点:

pip install "distilabel[hf-transformers,outlines,instructor]"
  • 除transformers外,也可改用vllm或hf-inference-endpoints作为 LLM 后端;
  • 数据源不必局限于字典:可先用datasets的load_dataset从 Hub 加载数据,再通过pipeline.run(dataset=dataset)喂给流水线;
  • 运行完成后记得用distiset.push_to_hub(...)把数据集推送到 Hub。

相关练习的指令数据集版本见 instruction_sft_dataset.ipynb,英文版偏好数据集文档见 v1/6_synthetic_datasets/preference_datasets.md,合成数据三大分类总览见 v1/6_synthetic_datasets/README.md。

参考资料

  • Distilabel 官方文档;
  • Deita 论文(arXiv 2312.15685);
  • UltraFeedback 论文(arXiv 2310.01377)。
  • 教程
  • 人工智能
  • 大模型
  • NLP
  • 微调

【免费下载链接】smol-course

A course on aligning smol models.

项目地址:https://gitcode.com/gh_mirrors/smo/smol-course
点击查看免费下载

相关推荐

上一篇:RT-Thread RA4M1 板级支持包实战:在瑞萨 EK-RA4M1 开发板上构建、烧录并运行 RTOS 应用
下一篇:3分钟掌握GitHub资源加速服务:raw.githack.com完整指南

创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询