TRL 为视觉语言模型添加直接偏好优化支持
TL;DR
Hugging Face 宣布 TRL 库现在支持视觉语言模型(VLM) 的直接偏好优化(DPO),使开发者能够使用偏好数据微调 Idefics‑2、Llava 1.5 和 PaliGemma 等模型,同时通过 bfloat16 量化和 LoRA 适配器保持内存需求可控。
基于偏好的 VLM 微调
偏好优化用二元比较取代了昂贵的标签监督:每个训练样本包含一个提示、一个 chosen(选定)答案和一个 rejected(拒绝)答案。模型学习为选定的响应分配更高的概率。该方法捕捉细微的人类判断,已被广泛用于语言模型;新的 TRL 集成将其扩展到多模态 VLM。
示例数据集
博客使用 openbmb/RLAIF‑V‑Dataset,该数据集提供 83 k+ 行图像‑问题对,并附有选定和拒绝的文本答案。示例条目如下:
Question: "How many families?"
Rejected: "The image does not provide any information about families."
Chosen: "The image shows a Union Organization table setup with 18,000 families."
选定的答案仍可能在事实层面不完全正确,但它比被拒绝的答案错误程度更小,这正是偏好学习的核心前提。
面向聊天式 VLM 的格式化
需要将数据集重塑为聊天格式,即用户提供图像和文本查询,助理回复选定或拒绝的文本。使用 Hugging Face AutoProcessor(例如 HuggingFaceM4/idefics2-8b)来应用聊天模板并将图像调整到处理器的最大边长,以防止内存不足(OOM)错误。下面的代码片段演示了该转换:
from datasets import features
from transformers import AutoProcessor
processor = AutoProcessor.from_pretrained("HuggingFaceM4/idefics2-8b", do_image_splitting=False)
def format(example):
prompt = [{"role": "user", "content": [{"type": "image"}, {"type": "text", "text": example["question"]}]}]
chosen = [{"role": "assistant", "content": [{"type": "text", "text": example["chosen"]}]}]
rejected = [{"role": "assistant", "content": [{"type": "text", "text": example["rejected"]}]}]
prompt = processor.apply_chat_template(prompt, tokenize=False)
chosen = processor.apply_chat_template(chosen, tokenize=False)
rejected = processor.apply_chat_template(rejected, tokenize=False)
max_size = processor.image_processor.size["longest_edge"]
example["image"].thumbnail((max_size, max_size))
return {"images": [example["image"]], "prompt": prompt, "chosen": chosen, "rejected": rejected}
在数据集上映射此函数并将 images 列转换为解码后的 PIL.Image 对象后,数据即可用于训练。
使用 DPO 训练 VLM
博客演示了以 Idefics‑2‑8b 为参考模型进行微调,但相同的流水线同样适用于 Llava 1.5 和 PaliGemma。
内存预算
训练一个全精度 8 B 参数模型大约需要 160 GB 的显存(模型、参考副本、梯度和 AdamW 状态)。作者展示了逐步计算过程:
| 组件 | 每参数字节数 | 总计 (GB) |
|---|---|---|
| 模型(训练) | 4 (float32) | 32 |
| 参考模型 | 4 | 32 |
| 梯度 | 4 | 32 |
| 优化器状态(2×) | 4 | 64 |
| 总计 | – | 160 |
由于大多数 GPU 的显存远小于此,博客推荐两种互补技术。
量化为 bfloat16
切换到 torch.bfloat16 将每参数存储从 4 字节减半至 2 字节,使模型内存从 32 GB 降至 16 GB。此更改同时应用于模型和优化器:
model = AutoModelForVision2Seq.from_pretrained(..., torch_dtype=torch.bfloat16)
training_args = DPOConfig(..., bf16=True)
通过 PEFT 使用 LoRA 适配器
低秩适配(LoRA)冻结基础模型,并在线性层中注入可训练的秩分解矩阵。使用 peft.LoraConfig(target_modules="all-linear") 将可训练参数从 8 B 降至约 55 M(≈0.65 % 的总量)。梯度和优化器状态的内存现在降至几百兆字节。
在量化和 LoRA 之后重新计算预算,得到 ≈32 GB 的总内存,轻松适配 80 GB GPU。
批量大小与激活内存
激活内存未计入静态预算。作者建议采用经验方法:先设定期望的批量大小(例如 64),观察 OOM,若出现则将批量大小减半,并将 gradient_accumulation_steps 加倍,以保持有效批量大小不变。在他们的实验中,最终使用 per_device_train_batch_size=2 和 gradient_accumulation_steps=32。启用 gradient_checkpointing=True 可进一步降低激活内存,但会增加计算量。
完整训练脚本
一个独立脚本(dpo_idefics2-8b.py)将模型加载、数据集格式化、LoRA 配置以及 DPOTrainer 结合在一起。关键参数包括:
bf16=Trueandgradient_checkpointing=Trueper_device_train_batch_size=2,gradient_accumulation_steps=32- Parallel preprocessing with
dataset_num_proc=32anddataloader_num_workers=32 LoraConfig(target_modules="all-linear")passed toDPOTrainer
使用 accelerate launch dpo_idefics2-8b.py 运行脚本即可启动单轮次的 DPO 微调。
训练结果
损失曲线显示两项 DPO 特定指标稳步提升:
- Accuracy – 模型为选定答案分配更高概率的样本比例。
- Reward margin – 选定答案与拒绝答案的奖励(对数概率)差值;差距增大表明偏好学习成功。
两项指标在训练过程中均上升,证实 DPO 能有效引导 VLM 产生偏好的响应。
对幻觉降低的评估
为了评估 DPO 是否能减轻幻觉,微调后的 Idefics‑2 模型在 AMBER 基准(针对 VLM 的幻觉测试)上进行评估。结果(准确率 / F1)如下:
| 模型 | 准确率 | F1 |
|---|---|---|
| GPT‑4o | 88.8 | 91.6 |
| Idefics‑2 + DPO | 85.9 | 89.4 |
| Idefics‑2 (baseline) | 85.8 | 89.1 |
| GPT‑4v | 83.4 | 87.4 |
| MiniGemini | 82.6 | 87.6 |
| … | … | … |
DPO 微调模型的表现与基线相当或略有提升,表明幻觉有所降低。
定性示例
挑选的 AMBER 示例展示了变化:
| Image | 问题 | 基线 Idefics‑2 | Idefics‑2 + DPO |
|---|---|---|---|
| ![ships] | Are there two ships? | Yes | No |
| ![ground] | Is the ground uneven? | No | Yes |
| ![shovel] | Is there one shovel? | Yes | No |
这些示例表明模型在训练数据指示偏好时,会倾向于选择更少幻觉的答案。
将 DPO 扩展到其他 VLM
TRL 的 DPO 实现已支持 Llava 1.5 和 PaliGemma。博客提供了 TRL 仓库中的示例脚本(examples/scripts/dpo_vlm.py)。对于 PaliGemma,典型的命令行如下:
accelerate launch examples/scripts/dpo_visual.py \
--dataset_name HuggingFaceH4/rlaif-v_formatted \
--model_name_or_path google/paligemma-3b-pt-224 \
--per_device_train_batch_size 2 \
--gradient_accumulation_steps 32 \
--dataset_num_proc 32 \
--output_dir dpo_paligemma_rlaif-v \
--bf16 \
--torch_dtype bfloat16 \
--gradient_checkpointing \
--use_peft \
--lora_target_modules=all-linear
相同的量化 + LoRA 方案适用,使得在普通 GPU 硬件上也能使用 DPO。
含义
通过在 TRL 中为 VLM 集成 DPO,Hugging Face 降低了基于偏好的多模态模型微调门槛。开发者现在可以在无需昂贵标签收集的情况下,使 VLM 与人类判断保持一致,同时仍在单个高端 GPU 的内存限制内。AMBER 上的轻微幻觉改进表明,偏好数据可以作为降低过度自信错误的有效信号,为构建更安全、更可信的视觉语言助手铺平道路。
TL;DR – 新的 TRL DPO 支持让您可以使用二元偏好数据微调视觉语言模型,并通过 bfloat16 量化加 LoRA 适配器,在单块 80 GB GPU 上训练 8 B 参数的 VLM,获得偏好准确率的可衡量提升以及幻觉的降低。