RLHF人类反馈强化学习对齐训练完整流程

RLHF(Reinforcement Learning from Human Feedback)是大模型开发过程中对齐人类价值观的核心训练方法。ChatGPT、Claude、Llama等主流模型均在预训练后使用RLHF进行对齐训练,使模型输出更安全、更有用、更符合人类预期。RLHF对齐训练的完整流程包含三个阶段:SFT监督微调、RM奖励模型训练、PPO强化学习优化。每个阶段的数据准备、超参数配置和训练技巧直接影响最终模型质量,机器学习算法在这一过程中扮演关键角色。

RLHF对齐训练三阶段流程概述

RLHF的三个阶段构成递进关系。SFT阶段用高质量对话数据对预训练模型做监督微调,让模型学会指令跟随。RM阶段训练一个打分模型,学习人类对回答质量的偏好排序。PPO阶段用奖励模型的分数作为强化学习的奖励信号,通过近端策略优化算法微调SFT模型,使其生成高分回答。三个阶段共享基础模型架构,但训练目标和数据格式各不相同。

SFT监督微调阶段的数据构造与训练

SFT阶段的数据格式为指令-回答对。每条数据包含用户输入(instruction)和期望输出(response)。数据质量比数量更重要,5000条精心标注的对话数据往往优于5万条低质量数据。

训练代码示例(基于HuggingFace transformers):

from transformers import AutoModelForCausalLM, AutoTokenizer
from trl import SFTTrainer, SFTConfig
from datasets import Dataset

model_path = "meta-llama/Llama-3-8B"
tokenizer = AutoTokenizer.from_pretrained(model_path)
model = AutoModelForCausalLM.from_pretrained(model_path, torch_dtype="auto")

sft_data = Dataset.from_list([
    {"instruction": "解释什么是梯度消失", "response": "梯度消失是指..."}
])

def format_example(ex):
    text = f"### Human: {ex['instruction']}\n### Assistant: {ex['response']}"
    return {"text": text}

sft_data = sft_data.map(format_example)

config = SFTConfig(
    output_dir="./sft_model",
    num_train_epochs=3,
    per_device_train_batch_size=4,
    gradient_accumulation_steps=8,
    learning_rate=2e-5,
    warmup_ratio=0.03,
    lr_scheduler_type="cosine",
    bf16=True,
    max_seq_length=2048,
)

trainer = SFTTrainer(
    model=model,
    train_dataset=sft_data,
    args=config,
)
trainer.train()
trainer.save_model("./sft_model")

SFT阶段的关键超参数:学习率通常设为1e-5到5e-5,过大会导致灾难性遗忘,过小则训练不充分。epoch数一般2-3轮,过多会导致过拟合。bf16或fp16混合精度训练能显著降低显存占用。

RM奖励模型训练的偏好数据与损失函数

RM阶段的训练数据为偏好对(preference pairs)。每条数据包含一个prompt和两个回答(chosen和rejected),标注人员从中选择更好的回答。RM模型通常与SFT模型共享架构,但输出层改为标量(奖励分数)。

RM训练使用Bradley-Terry偏好模型,损失函数为:

import torch
import torch.nn as nn

class PreferenceLoss(nn.Module):
    def __init__(self):
        super().__init__()

    def forward(self, chosen_rewards, rejected_rewards):
        loss = -torch.log(
            torch.sigmoid(chosen_rewards - rejected_rewards)
        )
        return loss.mean()

loss_fn = PreferenceLoss()
optimizer = torch.optim.AdamW(rm_model.parameters(), lr=5e-6)

for batch in dataloader:
    chosen_ids = batch["chosen_input_ids"]
    rejected_ids = batch["rejected_input_ids"]

    chosen_rewards = rm_model(chosen_ids).logits.squeeze(-1)
    rejected_rewards = rm_model(rejected_ids).logits.squeeze(-1)

    loss = loss_fn(chosen_rewards, rejected_rewards)
    loss.backward()
    optimizer.step()
    optimizer.zero_grad()

RM训练中偏好数据的一致性至关重要。同一prompt下的chosen和rejected质量差异要明确,标注一致性低于70%的数据应剔除。RM模型不宜训练过久,通常1-2轮epoch即够,过拟合会导致PPO阶段奖励信号失真。

PPO强化学习优化的核心实现

PPO阶段涉及四个模型:Actor(待优化的策略模型)、Critic(价值函数)、Reference(冻结的SFT模型,用于KL惩罚)、Reward(冻结的RM模型,提供奖励信号)。训练时Actor生成回答,Reward打分,Critic估计基线价值,通过PPO的clip目标函数更新Actor和Critic。

from trl import PPOTrainer, PPOConfig, AutoModelForCausalLMWithValueHead

actor_model = AutoModelForCausalLMWithValueHead.from_pretrained("./sft_model")
ref_model = AutoModelForCausalLMWithValueHead.from_pretrained("./sft_model")
ref_model.eval()
for p in ref_model.parameters():
    p.requires_grad = False

ppo_config = PPOConfig(
    model_name="./sft_model",
    learning_rate=1e-5,
    batch_size=32,
    mini_batch_size=4,
    ppo_epochs=4,
    kl_penalty="kl",
    target_kl=6.0,
    init_kl_coef=0.2,
    cliprange=0.2,
)

ppo_trainer = PPOTrainer(
    config=ppo_config,
    model=actor_model,
    ref_model=ref_model,
    tokenizer=tokenizer,
)

for batch in ppo_dataloader:
    query_tensors = batch["query"]
    response_tensors = ppo_trainer.generate(
        query_tensors,
        max_new_tokens=256,
        do_sample=True,
        top_p=0.9,
    )
    texts = [tokenizer.decode(q + r) for q, r in zip(query_tensors, response_tensors)]
    rewards = rm_model.get_rewards(texts)
    stats = ppo_trainer.step(query_tensors, response_tensors, rewards)
    print(f"KL: {stats['objective/kl']:.4f}, Reward: {stats['ppo/returns/mean']:.4f}")

PPO训练的KL散度控制与常见问题

KL散度惩罚是PPO阶段防止模型偏离SFT分布的关键机制。target_kl通常设为6.0-10.0,KL系数初始0.1-0.2。当实际KL超过target_kl的两倍时应停止当前epoch更新,否则模型会reward hacking——生成语法怪异但奖励分数高的回答。

常见问题排查:

1. 奖励先升后骤降:检查RM是否过拟合,或KL惩罚过弱导致reward hacking。降低学习率或增大init_kl_coef。

2. 生成内容退化(重复、空话):PPO训练轮次过多。每个prompt batch的ppo_epochs不超过4,总训练步数根据reward曲线停止。

3. KL持续接近0:Actor几乎没被更新。检查学习率是否过小,或reward差异是否过小(chosen和rejected分数接近)。

DPO直接偏好优化作为RLHF的替代方案

DPO(Direct Preference Optimization)跳过RM训练和PPO强化学习阶段,直接用偏好数据优化SFT模型。损失函数基于偏好数据的似然比,理论上等价于RLHF但训练更简单稳定。

from trl import DPOTrainer, DPOConfig

dpo_config = DPOConfig(
    output_dir="./dpo_model",
    num_train_epochs=1,
    per_device_train_batch_size=4,
    learning_rate=5e-7,
    beta=0.1,
    max_length=2048,
    max_prompt_length=1024,
)

trainer = DPOTrainer(
    model=AutoModelForCausalLM.from_pretrained("./sft_model"),
    ref_model=AutoModelForCausalLM.from_pretrained("./sft_model"),
    args=dpo_config,
    train_dataset=preference_dataset,
    tokenizer=tokenizer,
)
trainer.train()

DPO的beta参数控制偏离SFT模型的强度,0.1是常见起点值。降低beta使模型更激进地学习偏好,增大beta使模型更保守。DPO训练效率比PPO高数倍,但PPO在需要在线采样的复杂对齐场景下仍有优势。

对齐效果评估指标

RLHF完成后需评估对齐效果。自动评估指标包括:RM测试集准确率(chosen被选中的比例)、奖励分布(生成回答的平均奖励分数)、KL散度(与SFT模型的偏离程度)。人工评估采用Elo评分或Win Rate:让人类或GPT-4在SFT模型输出和RLHF模型输出之间盲选,统计胜率。RLHF模型在helpfulness和safety指标上的胜率应显著高于SFT基线。

原创文章,作者:小编,如若转载,请注明出处:https://www.yunthe.com/rlhf-ren-lei-fan-kui-qiang-hua-xue-xi-dui-qi-xun-lian-wan/

(0)
小编小编
上一篇 3小时前
下一篇 2小时前

相关推荐