TRL v1.0がメジャーリリース、LLMポストトレーニングの安定基盤へ
HuggingFaceのLLMポストトレーニングライブラリ TRL(Transformers Reinforcement Learning) が、最初のコード公開から6年以上を経て、初の正式版となるv1.0をリリースした。月間300万ダウンロード、GitHubでの「いいね」(Stars)が17,800件を超える規模のライブラリが、「開発途中のプロジェクト」から「安定して使える部品」への転換を宣言した形になる。
背景にあるのは、UnslothやAxolotlといったTRLを土台にして作られたツールが、既に実際の運用で使われている現実だ。「ここは変えないでね」という暗黙の約束が既にあったものを、バージョン番号のルールとして明文化した。このルールは「セマンティックバージョニング」と呼ばれ、「1.0.0」のような3桁の番号でソフトウェアを管理する。先頭の数字が上がったら「使い方が大きく変わった」サイン、真ん中なら「新機能が増えた」、末尾なら「バグを直しただけ」と、番号を見るだけで変更の規模がわかる仕組みだ。
Stable/Experimental二層モデル
v1.0の核は、ライブラリの機能の呼び出し方(API、プログラムから機能を使うための窓口)を「安定版」と「実験版」の二層に分けた構造にある。
from trl import SFTTrainer # stable
from trl.experimental.orpo import ORPOTrainer # experimental
Stableに含まれるのはSFT、DPO、Reward Modeling、RLOO、GRPOとその派生版。これらはバージョン番号の安定保証の対象で、使い方が大きく変わる場合はバージョンの先頭の数字が上がるので、利用者は事前に気づける。
Experimental(実験版)には75以上の手法が含まれる。KTO、ORPO、CPO、SimPO、IPO、GKD、SDFT、SDPO、GOLDなど、名前だけ見ると大量にあるが、すべてLLMの振る舞いを調整する手法のバリエーションだ。こちらは使い方が予告なく変わる可能性がある代わりに、研究の最新動向に即座に追従できる。
この分離はライブラリ全体の設計方針と直結している。
意図的な重複を許容する設計
TRLが採用した設計方針は、プログラミングの教科書に載っている「良い設計」とは逆方向を向いている。普通なら「共通する機能は1箇所にまとめて使い回す」のが定石だが、TRLはあえて各Trainer(訓練を実行するプログラム部品)に似たようなコードを重複して持たせている。
# TRLが避けるパターン
class OfflineTrainer(Trainer):
def some_common_method(self): ...
class DPOTrainer(OfflineTrainer): ...
class KTOTrainer(OfflineTrainer): ...
# TRLが採用するパターン
class DPOTrainer(Trainer):
def some_common_method(self): ...
class KTOTrainer(Trainer):
def some_common_method(self): ...
理由は明快で、ポストトレーニングの分野は変化が速すぎる。半年前に「ここは共通だろう」とまとめた部分が、今日には足枷になる。たとえばDPOとKTOでデータの下準備が同じに見えても、実際には入力データの形が違う(「良い回答と悪い回答の2つ組」を使うか「回答1つだけ」を使うか)ので、共通化すると片方を変えたときにもう片方まで壊れる。ブログでは「前提がすぐ覆る領域では、コードの重複こそが正しい設計判断だ」と述べている。
以前取り上げた 16のオープンソースRLライブラリの比較分析 でも、各ライブラリの設計の違いが浮き彫りになっていたが、TRL自身がその多様性に耐えるための設計判断を下したことになる。
ポストトレーニングの全体像
記事中にSFT、DPO、GRPOと略語が飛び交っているが、そもそもポストトレーニングが何をする段階なのかを整理しておく。
LLMの訓練工程は大きく2段階に分かれる。
graph LR
A["事前学習<br/>(Pre-training)"] --> B["ポストトレーニング<br/>(Post-training)"]
B --> C[デプロイ]
事前学習は、インターネット上の膨大なテキストから言語のパターンを学ぶ段階だ。数兆単語分のデータと、数千台のGPU(画像処理だけでなくAI計算にも使われる高性能チップ)を使って数ヶ月かかる。MetaのLLaMAやMistral社のMistralなど、よく名前を聞くモデルの「素」(ベースモデル)がこの段階で生まれる。ベースモデルは文章の続きを予測する能力は持つが、質問に答えたり指示に従ったりする能力はまだない。
ポストトレーニングは、この事前学習済みモデルに「望ましい振る舞い」を教える段階だ。TRLが扱うのはこちらで、Stableに入った5系統はそれぞれ異なるアプローチを取る。
| 手法 | やること | 必要なデータ |
|---|---|---|
| SFT | 「こう答えるのが正解」という手本を見せて真似させる | 質問と模範解答のセット |
| Reward Modeling | 応答の良し悪しを自動で点数づけするモデルを作る | 人間が「AよりBの回答が良い」と判定したデータ |
| DPO | 採点モデルを使わず「良い回答/悪い回答」のペアから直接学ぶ | 良い応答と悪い応答のペア |
| RLOO | 複数の回答を出して、他の回答との比較で学ぶ強化学習 | 質問と採点ルール |
| GRPO | グループで回答を出し合い、グループ内の相対評価で学ぶ強化学習 | 質問と採点ルール |
典型的な流れでは、まずSFTで「指示に従って答える」という基本動作を教え、次にRLHF(人間のフィードバックを使った強化学習。人間の「こっちの回答のほうがいいね」という判断をAIに学ばせる手法)系の手法で「より人間好みの回答」に仕上げる。
graph TD
A[ベースモデル] --> B["SFTで指示に従う力を学習"]
B --> C{"仕上げ方法の選択"}
C -->|採点モデルを作る| D[Reward Model訓練]
D --> E["PPO / RLOO / GRPOで強化学習"]
C -->|採点モデル不要| F["DPOで直接学習"]
E --> G[実用可能なモデル]
F --> G
近年はDeepSeek-R1やOpenAI o1のように、「ステップを踏んで論理的に考える力」を伸ばすためにGRPOやPPOを活用するケースが増えている。「人間好みに合わせる」だけでなく「正しく推論させる」方向にポストトレーニングの守備範囲が広がった。TRLのStable層にGRPOが入ったのは、この流れを反映している。
GRPOとは何か
Stableに入った手法の中で特に注目すべきはGRPO(Group Relative Policy Optimization)だ。中国のAI企業DeepSeekが DeepSeekMath という論文で提案し、後にDeepSeek-R1の訓練で広く知られるようになった。
従来のPPO(Proximal Policy Optimization)では、回答を生成するモデル本体とは別に、「この回答はどれくらい良さそうか」を予測する採点役モデルが必要だった。この採点役は本体と同じくらい巨大になることが多く、GPUのメモリ(VRAM、GPUが作業に使える記憶領域)も計算コストも2倍かかっていた。
GRPOはこの採点役モデルを丸ごと廃止した。代わりの仕組みはシンプルで、1つの質問に対して複数の回答をまとめて生成し、その中での相対的な出来の良さで評価する。学校のテストに例えると、「80点以上が合格」のように絶対的な基準で採点する先生をクビにして、「同じクラスの中で偏差値が高い人が優秀」という相対評価に切り替えたイメージだ。
| 項目 | PPO | GRPO |
|---|---|---|
| 採点役モデル | 必要(本体と同規模) | 不要 |
| 評価の基準 | 採点役の予測値 | グループ内の平均スコア |
| GPUメモリ消費 | 大(モデル2本分) | 小(モデル1本分) |
| コスト効率 | 基準 | 最大18倍効率的 |
DeepSeekの報告では、数学の問題を解く性能テストでGSM8K(小学校レベルの算数テスト)が82.9%→88.2%、MATH(高校〜大学レベルの数学テスト)が46.8%→51.7%と、採点役モデルを使うPPO方式と比べても同等以上の成績改善を達成している。
graph TD
A[質問を入力] --> B[モデルが<br/>G個の回答を一括生成]
B --> C[各回答にスコアをつける]
C --> D[グループ内で<br/>スコアを相対評価に変換]
D --> E[どの回答が良かったか<br/>差分を計算]
E --> F[良い回答の傾向を<br/>強化するようモデル更新]
F --> G[元のモデルから<br/>離れすぎないよう制御]
G --> A
競合ライブラリとの位置づけ
TRLが狙っているのは最高性能より導入のしやすさだ。ブログ内で公開された比較表が興味深い。
| ライブラリ | 月間DL | Semver | 必要な設備規模 |
|---|---|---|---|
| TRL | 300万 | 安定 | 低(単一GPU可) |
| OpenRLHF | 3,600 | 部分的 | 高 |
| veRL | 10.2万 | 部分的 | 高 |
| LLaMA-Factory | 36.3万 | 部分的 | 中 |
ダウンロード数で圧倒的な差があるのは、HuggingFaceのツール群との連携の良さが理由だろう。LoRA/QLoRA(モデル全体ではなくごく一部だけを調整する省メモリ技術)が標準で使え、モデル共有サイトHF Hubとの連携やVLM(Vision Language Model、画像と言語の両方を扱うモデル)の訓練にも対応している。
一方で、1つのモデルを複数GPUに分割して同時に計算するテンソル並列は標準機能としては未対応。複数台のマシンに作業を分散させる訓練(DeepSpeed/FSDPという仕組みを利用)は使えるが、数十〜数百台のGPUを使う大規模環境での性能ではverlやOpenRLHFに分がある。
非同期GRPOのロードマップ
ロードマップ(今後の開発予定)の筆頭に挙がっているのが非同期GRPOだ。現在のTRLにおけるGRPO訓練は、回答の生成→スコア計算→モデル更新が一直線に順番待ちで進む。回答生成で長い思考過程(Chain of Thought。8K〜32Kトークン、日本語にしておよそ数千〜1万文字ぶん)が必要だと、その間モデル更新用のGPUが暇を持て余してしまい、GPUの稼働率が60%程度まで落ちる。
非同期GRPOでは回答の生成とモデルの更新を別々のGPUで同時進行させる。生成側は休みなく回答を作り続け、更新側は溜まった結果をどんどん処理する。工場のベルトコンベアのように、前の工程が終わるのを待たずに次の工程が動き続けるイメージだ。生成が速すぎて更新が追いつかないときは生成側にブレーキをかけ、モデルの状態がずれすぎないよう管理する。設計自体は既に存在しているとのことで、先日の比較分析で取り上げたverlやAReaLが先行実装している非同期分離型の設計と同じ方向性だ。
他のロードマップ項目として、KTO・SDFT・SDPO・GOLDなどExperimental手法のStable昇格、MoE(「得意分野が違う複数の小さなモデル」を組み合わせて1つの大きなモデルとして動かす仕組み)の並列対応、そしてAIエージェントが訓練の様子を監視しやすくする改善がある。最後の項目が面白くて、訓練中にGPUメモリの使用率が低すぎる、スコアのばらつきがなくなった(学習が止まったサイン)、などの異常を自動で警告してくれる仕組みだ。
[TRL] WARNING: VRAM utilization at 34%. Consider increasing
per_device_train_batch_size from 4 to 16.
[TRL] WARNING: Group reward std is 0.01 (near zero).
Advantage signal has collapsed.
人間が訓練の記録を逐一監視しなくても、あるいはAIエージェントが訓練工程を自動運用する場合でも、問題を早期検出できるようにする狙いがある。
v1.0が意味するもの
Stable層に入ったのはSFT・DPO・GRPO・RLOO・Reward Modelingの5系統だけ。75以上ある手法の大半はExperimental(実験版)のままだ。DeepSeek-R1がGRPOを広めた2024年から2年足らずで75以上の手法が乱立している現状を考えると、v1.0は「分野が安定した」という宣言ではなく「どこが安定でどこが不安定か」の線引きだ。
実際に何を訓練するのか
手法の解説が続いたので、TRLで具体的に何をやるのかを作業レベルで補足しておく。
典型的なユースケースは大きく2つある。
1つ目は、特定の仕事に特化させることだ。たとえば社内文書に特化したチャットボットを作る場合、LLaMA 3.1 8B(パラメータ、つまり「脳のシナプスにあたる数値」が80億個のモデル)を出発点に、SFTで社内Q&Aデータ(数千〜数万件)を学習させ、DPOでユーザーの好みを反映する。先述のQLoRAを使えば、この工程全体がゲーミングPC1台(RTX 4090、GPUメモリ24GB)で動く。大学や企業の研究所レベルの設備がなくても実験できるのがTRLの現実的な強みだ。
2つ目は、論理的に考える力の強化だ。DeepSeek-R1で注目されたやり方で、数学やプログラミングなど「答えが合っているか自動で確認できる」課題にGRPOを適用する。
from trl import GRPOTrainer, GRPOConfig
# 報酬関数: 正解なら+1、不正解なら-1
def reward_fn(completions, **kwargs):
return [1.0 if verify(c) else -1.0 for c in completions]
trainer = GRPOTrainer(
model="Qwen/Qwen2.5-1.5B",
reward_funcs=[reward_fn],
args=GRPOConfig(
num_generations=8, # プロンプトごとに8個の応答を生成
output_dir="./grpo_output",
),
)
trainer.train()
採点ルール(報酬関数、「正解なら+1点、不正解なら-1点」のようにスコアを返すプログラム)で「正しい答えかどうか」を自動判定し、正解にたどり着く思考の道筋を強化学習で伸ばす。人間がいちいち「この回答はいい」「これはダメ」と判定する必要がなく、正解を自動チェックできる課題なら完全自動で訓練が回せる。DeepSeekの報告ではこの手法でGSM8Kの正解率が5ポイント以上改善しており、小さなモデルでも論理的に考える力を引き出せることが示されている。