🧠LoRA ファインチューニング ハイパーパラメータガイド

最適な LoRA ランク、alpha、エポック数、バッチサイズと勾配蓄積、QLoRA と LoRA の比較、ターゲットモジュールなど!

LoRA ハイパーパラメータは、Low-Rank Adaptation (LoRA) が大規模言語モデル(LLM)をファインチューニングする際に制御する調整可能なパラメータです。学習率やエポック数など多くのオプションがあり、組み合わせは何百万通りにもなるため、適切な値を選ぶことは、ファインチューニング中の精度、安定性、品質、そして幻覚の減少を達成するために極めて重要です。

ここでは、何百もの研究論文や実験から得られた知見に基づくこれらのパラメータのベストプラクティスを学び、それらがモデルにどのような影響を与えるかを確認します。 Unsloth のデフォルトの使用を推奨しますが、これらの概念を理解することで完全な制御が可能になります。 目的は、精度を上げつつ 過学習または学習不足に対抗することです。過学習はモデルが訓練データを丸暗記してしまい、新しい未見の入力に対して一般化する能力を損なう場合に起こります。目標は単に記憶するモデルではなく、よく一般化するモデルを得ることです。

では、LoRA とは何でしょうか?

LLM ではモデルの重み(ウェイト)があります。Llama 70B には 700 億の数値があります。すべての 70b の数値を変更する代わりに、各重みへ薄い行列 A と B を追加し、それらを最適化します。これにより最適化するのは重みのわずか 1% だけになります。

モデル重み(黄色)を最適化する代わりに、2つの薄い行列AとBを最適化します。

🔢 重要なファインチューニングのハイパーパラメータ

学習率(Learning Rate)

各トレーニングステップでモデルの重みがどの程度調整されるかを定義します。

  • 高い学習率: 初期の収束は速くなりますが、設定が高すぎるとトレーニングが不安定になったり、最適な最小値を見つけられなかったりします。

  • 低い学習率: より安定で精密なトレーニングになりますが、収束により多くのエポックを必要とするため、全体のトレーニング時間が増える可能性があります。低い学習率はしばしば学習不足を引き起こすと考えられますが、実際には 過学習 や場合によってはモデルが学習するのを妨げることさえあります。

  • 典型的な範囲: 2e-4 (0.0002)から 5e-6 (0.000005). 🟩 通常の LoRA/QLoRA ファインチューニングでは, 開始点として推奨します。 2e-4 を出発点として推奨します。 🟦 強化学習の場合 (DPO、GRPO 等)には、我々は以下を推奨します: 5e-6 . フルファインチューニングの場合、 より低い学習率の方が一般的に適切です。

エポック(Epochs)

モデルが完全な訓練データセットを何回見るかの回数です。

  • エポック数が多い場合: モデルの学習を助けることがありますが、多すぎると 訓練データを暗記してしまうことで新しいタスクでの性能が損なわれます。

  • エポック数が少ない場合: トレーニング時間を短縮でき、過学習を防ぐことができますが、データセットの基礎的なパターンを学習するのに不十分であれば、モデルが十分に学習されていない結果になる可能性があります。

  • 推奨: 1~3 エポック。ほとんどの指示ベースのデータセットでは、3 エポックを超えてトレーニングしても利得は薄れ、過学習のリスクが高まります。

LoRA または QLoRA

LoRA は 16 ビット精度を使用し、QLoRA は 4 ビットのファインチューニング手法です。

  • LoRA: 16 ビットのファインチューニングです。わずかに高速でわずかに精度が高いですが、VRAM を大幅に多く消費します(QLoRA の約4倍)。16 ビット環境や最大精度が求められるシナリオに推奨されます。

  • QLoRA: 4 ビットのファインチューニングです。やや遅く、精度もわずかに劣りますが、使用する VRAM は格段に少なく(約4分の1)、効率的です。 🦥 Unsloth では QLoRA で 70B LLaMA が <48GB VRAM に収まります - 詳細はこちらarrow-up-right.

ハイパーパラメータと推奨事項:

ハイパーパラメータ
機能
推奨設定

LoRA ランク (r)

LoRA アダプタ行列で訓練可能なパラメータの数を制御します。ランクが高いほどモデルの容量は増えますが、メモリ使用量も増加します。

8、16、32、64、128 16 または 32 を選択

LoRA アルファ (lora_alpha)

ランクに対する微調整の強さをスケーリングします(r).

r (標準)または r * 2 (一般的なヒューリスティック)。 詳細はこちら.

LoRA ドロップアウト

トレーニング中に過学習を防ぐため、LoRA の活性化の一部をランダムにゼロにする正則化手法です。 あまり有用ではない、そのためデフォルトで 0 に設定します。

0(デフォルト)〜0.1

重み減衰(Weight Decay)

大きな重みにペナルティを与えて過学習を防ぎ、汎化性能を向上させる正則化項です。あまり大きな値は使わないでください!

0.01(推奨)〜0.1

ウォームアップステップ

トレーニング開始時に学習率を徐々に上げます。

総ステップ数の 5〜10%

スケジューラタイプ

トレーニング中に学習率を動的に調整します。

線形(linear) または コサイン(cosine)

シード(random_state)

結果の再現性を確保するための固定の数値です。

任意の整数(例: 42, 3407)

対象モジュール

LoRA アダプタを適用したいモデルの部分を指定します — アテンション、MLP、またはその両方です。

アテンション: q_proj、k_proj、v_proj、o_proj MLP: gate_proj、up_proj、down_proj

主要な線形層すべてを対象にすることを推奨: q_proj、k_proj、v_proj、o_proj、gate_proj、up_proj、down_proj.

🌳 勾配蓄積とバッチサイズの等価性

有効バッチサイズ

バッチサイズを正しく構成することは、トレーニングの安定性と GPU の VRAM 制限のバランスを取る上で重要です。これは 2 つのパラメータの積によって管理されます: 有効バッチサイズ. 有効バッチサイズ = batch_size * gradient_accumulation_steps

  • A より大きな有効バッチサイズは 一般的により滑らかで安定したトレーニングにつながります。

  • A より小さな有効バッチサイズは より多くの分散(バラつき)をもたらす可能性があります。

タスクごとに異なりますが、次の構成は安定した開始点を提供します: 有効バッチサイズ 16 の有効バッチサイズは、最新の GPU 上でほとんどのファインチューニング作業に適しています。

パラメータ
変数
推奨設定

バッチサイズ (batch_size)

1 台の GPU 上で単一のフォワード/バックワードパスで処理されるサンプル数。 VRAM 使用量の主な要因より高い値はハードウェアの利用効率を向上させ、トレーニングを高速化する可能性がありますが、メモリに収まる場合に限ります。

2

勾配蓄積 (gradient_accumulation_steps)

単一のモデル重み更新を行う前に処理するマイクロバッチの数。 トレーニング時間の主要な決定要因。 より大きな batch_size をシミュレートしてVRAMを節約します。値が大きいほどエポックごとのトレーニング時間が増加します。

8

有効バッチサイズ (計算)

各勾配更新に使用される真のバッチサイズ。トレーニングの安定性、品質、最終的なモデル性能に直接影響します。

4〜16 推奨: 16(2 * 8から)

VRAMとパフォーマンスのトレードオフ

トレーニングステップごとに32サンプルのデータを使用したいとします。すると次のいずれかの構成を使用できます:

  • batch_size = 32, gradient_accumulation_steps = 1

  • batch_size = 16, gradient_accumulation_steps = 2

  • batch_size = 8, gradient_accumulation_steps = 4

  • batch_size = 4, gradient_accumulation_steps = 8

  • batch_size = 2, gradient_accumulation_steps = 16

  • batch_size = 1, gradient_accumulation_steps = 32

これらはいずれもモデルの重み更新という点では同等ですが、ハードウェア要件は大きく異なります。

最初の構成(batch_size = 32)は 最も多くのVRAMを使用し、 ほとんどのGPUでは失敗する可能性が高いでしょう。最後の構成(batch_size = 1)は )は最小のVRAMで済みますが、 トレーニングがやや遅くなるという代償があります. OOM(メモリ不足)エラーを避けるため、常により小さい batch_size を設定し、目標の gradient_accumulation_steps に到達するために 有効バッチサイズ.

🦥 Unslothの勾配蓄積修正

勾配蓄積とバッチサイズ はUnslothでは現在完全に同等です 当社の勾配蓄積に関するバグ修正により、勾配蓄積が同じ結果を出さないという一般的な問題を解決しました。この課題は広く知られていましたが、Unslothのユーザーにとっては、これら二つの方法は現在互換性があり交換可能です。

私たちのブログ投稿を読むarrow-up-right で詳細を確認できます。

修正前は、同じ batch_size および gradient_accumulation_steps を生み出す組み合わせであっても、 有効バッチサイズ (すなわち、 batch_size × gradient_accumulation_steps = 16)は同等のトレーニング動作をもたらしませんでした。例えば、次のような構成は b1/g16, b2/g8, b4/g4, b8/g2、および b16/g1 はいずれも 有効バッチサイズ が16ですが、グラフに示されているように標準的な勾配蓄積を使用すると損失曲線が一致しませんでした:

(修正前 - 標準的な勾配蓄積)

当社の修正を適用した後は、16がどのように達成されたかにかかわらず、損失曲線は正しく整合します: 有効バッチサイズ (修正後 -

(修正後 - 🦥 Unsloth 勾配蓄積)

🦥 Unsloth における LoRA ハイパーパラメータ

以下は標準構成の例を示します。 Unsloth は最適化されたデフォルトを提供しますが、これらのパラメータを理解することは手動調整において重要です。

  1. ファインチューニングプロセスのランク(r)。ランクが大きいほどメモリを多く使用し遅くなりますが、複雑なタスクで精度を向上させる可能性があります。高速なファインチューニングには 8 や 16、最大で 128 などのランクを推奨します。ランクを大きくしすぎると過学習を引き起こし、モデルの品質を損なう可能性があります。\

  2. 最適なパフォーマンスのために、 LoRA はすべての主要な線形層に適用するべきです. 研究は示しています が、すべての主要層を対象にすることが完全なファインチューニングの性能に一致させるために重要であると。モジュールを除外してメモリ使用量を削減することは可能ですが、節約は最小限であるため最大の品質を保つため強くおすすめしません。\

  3. 微調整の調整強度を制御するスケーリング係数。ランクと等しく設定する(r)ことは信頼できるベースラインです。一般的で効果的な経験則はランクの2倍(r * 2)に設定することで、LoRA の更新により大きな重みを与え、モデルがより積極的に学習するようになります。 詳細はこちら.\

  4. 過学習を助ける正則化手法で、 過学習を防ぐ 各トレーニングステップで LoRA の活性化の一部をランダムにゼロにすることによって行います。 最近の研究は示唆していますarrow-up-right が、 短いトレーニング実行にとって ファインチューニングで一般的な、 lora_dropout は信頼できる正則化手法ではない可能性がある。 🦥 Unsloth の内部コードは、 lora_dropout = 0のときにトレーニングを最適化できるため、わずかに高速になりますが、過学習が疑われる場合は非ゼロ値を推奨します。\

  5. これを "none" のままにしておくと、トレーニングが速くなりメモリ使用量が減少します。この設定は線形層のバイアス項の学習を避けますが、実際的な利得はほとんどないため訓練可能なパラメータが増えることを避けます。\

  6. オプションは True, False、および "unsloth"です。 🦥 私たちは "unsloth" を推奨します。これはメモリ使用量をさらに30%削減し、非常に長いコンテキストのファインチューニングをサポートします。詳細は 長いコンテキストトレーニングに関する当社のブログ投稿arrow-up-right.\

  7. をお読みください。再現可能な実行を保証するためのシード。トレーニングには乱数が関与するため、固定シードを設定することは一貫した実験のために不可欠です。\

  8. 実装された高度な機能、 ランク安定化 LoRAarrow-up-right。もし Trueに設定されていると、実効スケーリングは lora_alpha / sqrt(r) ではなく lora_alpha / rになります。これは特に高いランクで安定性を改善することがあります。 詳細はこちら.\

  9. 高度な手法。提案元の LoftQarrow-up-rightでは、事前学習済み重みから上位 r 個の特異ベクトルで LoRA 行列を初期化します。これにより精度が向上する可能性がありますが、トレーニング開始時に大きなメモリスパイクを引き起こすことがあります。

LoRA 重みの更新の検証:

ファインチューニング後に LoRA アダプタ重みが更新されたことを検証する際、 np.allclose() を使用することは避けてください 比較のため。特に以下のような場合に、この方法では微妙だが意味のある変化を見逃すことがあります、 LoRA A(小さいガウス値で初期化される)。これらの変化は、緩い数値許容範囲では有意とみなされないことがあります。感謝します、 貢献者の皆さんarrow-up-right このセクションのために。

重みの更新を確実に確認するには、次を推奨します:

  • 使用すると、 チェックサムまたはハッシュ比較 (例:MD5)

  • を計算すること、 絶対差の合計 テンソル間で

  • テンソルの統計量を確認すること (例:平均、分散)を手動で

  • または np.array_equal() 厳密な等価性が期待される場合

📐LoRA の Alpha とランクの関係

circle-check
W^=W+αrank×AB\hat{W} = W + \frac{\alpha}{\text{rank}} \times AB
rsLoRA のその他のスケーリングオプション。sqrt(r) が最良です。
W^rslora=W+αrank×AB\hat{W}_{\text{rslora}} = W + \frac{\alpha}{\sqrt{\text{rank}}} \times AB

LoRA の式は左にあります。薄い行列 A と B をランクで割った alpha でスケールする必要があります。 つまり alpha/rank を少なくとも = 1 に保つべきです.

に従って、 rsLoRA(rank stabilized lora)論文arrow-up-rightでは、代わりに alpha をランクの平方根でスケールすべきだと述べられています。他の選択肢もありますが、理論的にはこれが最適です。左のプロットは他のランクとそのパープレキシティ(低いほど良い)を示しています。有効にするには、次を設定してください、 use_rslora = True Unsloth で。

私たちの推奨は、 alpha をランクと等しく、または少なくともランクの 2 倍に設定することです。 これは alpha/rank = 1 または 2 を意味します。

🎯 LoRA のターゲットモジュールと QLoRA 対 LoRA

circle-check

実験的結果や元のような研究論文によれば、 QLoRA 論文arrow-up-rightアテンションと MLP の両方に LoRA を適用するのが最良です。

図は異なるターゲットモジュール構成に対する RougeL スコア(高いほど良い)を示し、LoRA と QLoRA を比較しています。

最初の 3 つの点は次を示します:

  1. QLoRA-All: LoRA をすべての FFN/MLP と Attention レイヤーに適用。 🔥 これが全体的に最も性能が良いです。

  2. QLoRA-FFN:FFN のみに LoRA を適用。 同等なのは: gate_proj, up_proj, down_proj。

  3. QLoRA-Attention:Attention レイヤーのみに LoRA を適用。 同等なのは: q_proj, k_proj, v_proj, o_proj.

😎 入力をマスクして完了文のみでトレーニングすることは、

その QLoRA 論文arrow-up-right 入力をマスクして、 完了文のみでトレーニングすることを示しています (出力またはアシスタントのメッセージ)はさらに 精度を向上させることができます 数パーセントポイント(1%)。以下は Unsloth での実装例です:

ではありません 完了文のみでのトレーニング:

USER: こんにちは、2+2 は何ですか? ASSISTANT: 答えは 4 です。 USER: こんにちは、3+3 は何ですか? ASSISTANT: 答えは 6 です。

トレーニング 完了文のみで:

USER: こんにちは、2+2 は何ですか? ASSISTANT: 答えは 4 です。 USER: こんにちは、3+3 は何ですか? ASSISTANT: 答えは 6 です.

QLoRA 論文は、 完了文のみでのトレーニングが 精度をかなり向上させると述べており、特にマルチターンの会話型ファインチューニングで有効です!この方法は私たちの 会話用ノートブックにここでありますarrow-up-right.

レイヤーとしてではありません。これが量子化を複雑にします。特にMoE/MLPエキスパートは20Bパラメータのうち約19Bを占めます。 Unsloth での完了文でのトレーニングでは、instruction と assistant の部分を定義する必要があります。 将来的にはこれをさらに自動化する予定です! 🦥 Llama 3、3.1、3.2、3.3 および 4 モデルでは、部分は次のように定義します:

Gemma 2、3、3n モデルでは、部分は次のように定義します:

視覚モデル、VLM の場合のアシスタント応答のみでのトレーニング

🔎言語モデルの場合、前述のように

を使用できます。視覚モデルでは、追加の引数を from unsloth.chat_templates import train_on_responses_only UnslothVisionDataCollator の一部として使用してください、以前と同様に! class UnslothVisionDataCollator:

UnslothVisionDataCollator(

🔑 過学習

(一般化の失敗/過度に特化) モデルはトレーニングデータ(その統計的ノイズを含む)を記憶し、その結果、未知のデータに対して一般化できなくなります。

トレーニング損失が 0.2 を下回る場合、あなたのモデルはおそらく

circle-check

解決策:

  • 学習率を調整する: 高い学習率は短いトレーニングランでは過学習を招きやすいです。より長いトレーニングでは高い学習率がうまく機能する場合があります。どちらが最適かを確認するために両方を試すのが最良です。

  • トレーニングエポック数を減らす。1、2、または 3 エポックでトレーニングを停止してください。

  • 増やす weight_decay。値として 0.01 または 0.1 は良い出発点です。

  • 増やす lora_dropout。正則化を追加するために、 0.1 のような値を使用します。

  • バッチサイズまたは勾配蓄積ステップを増やす.

  • データセットの拡張 :データセットをオープンソースのデータセットと組み合わせたり連結したりして大きくします。より高品質なものを選んでください。

  • 評価による早期停止 :評価を有効にし、評価損失が数ステップ増加したら停止します。

  • LoRA Alpha スケーリング :トレーニング後および推論時に alpha をスケールダウンします — これによりファインチューニングの効果が目立ちにくくなります。

  • 重みの平均化 :元の instruct モデルとファインチューンを文字通り加算し、重みを 2 で割ります。

過少適合 (あまりに一般的)

モデルがトレーニングデータの基となるパターンを捉えられない場合で、複雑さやトレーニング時間が不足していることが原因であることが多いです。

解決策:

  • 学習率を調整する: 現在の学習率が低すぎる場合、学習率を上げることで収束が早まることがあります。短いトレーニングでは特に有効です。長いトレーニングでは学習率を下げてみてください。どちらが有効かを試してみてください。

  • トレーニングエポックを増やす: エポック数を増やしてトレーニングしますが、過学習を避けるために検証損失を監視してください。

  • LoRA ランクを上げる (r)と alpha:ランクは少なくとも alpha と等しくあるべきで、より小さいモデルやより複雑なデータセットではランクを大きくする必要があります。通常は 4 から 64 の間です。

  • よりドメインに関連したデータセットを使う:トレーニングデータが高品質でターゲットタスクに直接関連していることを確認してください。

  • バッチサイズを 1 に減らす。これによりモデルの更新がより激しくなります。

circle-check

謝辞: 心からの感謝を Eyeraarrow-up-right このガイドへの貢献に感謝します!

最終更新

役に立ちましたか?