跳转到主要内容

DPO 训练

直接偏好优化使模型与人类偏好对齐,无需奖励建模。

什么是 DPO?

DPO(Direct Preference Optimization)是 RLHF 的更简单替代方案。DPO 不是训练单独的奖励模型,而是直接优化模型以偏好选择的响应而非被拒绝的响应。

快速开始

aitraining llm --train \
  --model meta-llama/Llama-3.2-1B \
  --data-path ./preferences.jsonl \
  --project-name llama-dpo \
  --trainer dpo \
  --prompt-text-column prompt \
  --text-column chosen \
  --rejected-text-column rejected \
  --dpo-beta 0.1 \
  --peft
DPO 需要 --prompt-text-column--rejected-text-column--text-column 默认为 "text",因此只有当您的选择列名称不同时才需要指定。

Python API

from autotrain.trainers.clm.params import LLMTrainingParams
from autotrain.project import AutoTrainProject

params = LLMTrainingParams(
    model="meta-llama/Llama-3.2-1B",
    data_path="./preferences.jsonl",
    project_name="llama-dpo",

    trainer="dpo",
    prompt_text_column="prompt",
    text_column="chosen",
    rejected_text_column="rejected",
    dpo_beta=0.1,
    max_prompt_length=128,  # Default: 128
    max_completion_length=None,  # Default: None

    epochs=1,
    batch_size=2,
    gradient_accumulation=4,
    lr=5e-6,

    peft=True,
    lora_r=16,
    lora_alpha=32,
)

project = AutoTrainProject(params=params, backend="local", process=True)
project.create()

数据格式

DPO 需要偏好对:一个提示词和选择/拒绝的响应。
{
  "prompt": "What is the capital of France?",
  "chosen": "The capital of France is Paris.",
  "rejected": "France's capital is London."
}

多轮对话

{
  "prompt": [
    {"role": "user", "content": "What is AI?"},
    {"role": "assistant", "content": "AI is artificial intelligence."},
    {"role": "user", "content": "Give me an example."}
  ],
  "chosen": "A common example is ChatGPT, which uses AI to understand and generate text.",
  "rejected": "idk lol"
}

参数

参数描述默认值
trainer设置为 "dpo"必需
dpo_betaKL 惩罚系数0.1
max_prompt_length提示词最大 token 数128
max_completion_length响应最大 token 数None
model_ref参考模型(可选)None(使用基础模型)

Beta

beta 参数控制模型可以从参考模型偏离多少:
  • 0.01-0.05: 激进优化(可能过拟合)
  • 0.1: 标准(推荐)
  • 0.5-1.0: 保守(保持接近参考模型)
# 保守训练
params = LLMTrainingParams(
    ...
    trainer="dpo",
    dpo_beta=0.5,  # 更高 = 更保守
)

参考模型

model_refNone(默认值)时,DPO 使用初始模型作为参考。您可以指定不同的参考模型:
params = LLMTrainingParams(
    model="meta-llama/Llama-3.2-1B",  # 要训练的模型
    model_ref="meta-llama/Llama-3.2-1B-base",  # 参考模型
    ...
    trainer="dpo",
)

训练技巧

使用 LoRA

DPO 与 LoRA 配合良好:
params = LLMTrainingParams(
    ...
    trainer="dpo",
    peft=True,
    lora_r=16,
    lora_alpha=32,
    lora_dropout=0.05,
)

较低学习率

DPO 对学习率敏感:
params = LLMTrainingParams(
    ...
    trainer="dpo",
    lr=5e-7,  # 远低于 SFT
)

更少轮次

DPO 通常需要更少的轮次:
params = LLMTrainingParams(
    ...
    trainer="dpo",
    epochs=1,  # 通常 1-3 轮就足够
)

示例:有用助手

创建更有用的助手:
params = LLMTrainingParams(
    model="meta-llama/Llama-3.2-1B",
    data_path="./helpfulness_prefs.jsonl",
    project_name="helpful-assistant",

    trainer="dpo",
    dpo_beta=0.1,
    max_prompt_length=1024,
    max_completion_length=512,

    epochs=1,
    batch_size=2,
    gradient_accumulation=8,
    lr=1e-6,

    peft=True,
    lora_r=32,
    lora_alpha=64,

    log="wandb",
)

DPO vs ORPO

方面DPOORPO
参考模型必需不需要
内存使用更高更低
训练速度更慢更快
使用场景细粒度对齐组合 SFT + 对齐

收集偏好数据

人工标注

  1. 为每个提示词生成多个响应
  2. 让标注员对响应进行排序
  3. 创建选择/拒绝对

LLM 作为评判者

def create_preference_pairs(prompts, model_responses):
    """使用 GPT-4 判断哪个响应更好。"""
    # ... 生成判断
    return {"prompt": p, "chosen": better, "rejected": worse}

下一步