ディープラーニングにおけるデータ型: FP32、FP16、BF16、INT8、INT4の解説

スポンサーリンク

ディープラーニングにおけるデータ型: FP32、FP16、BF16、INT8、INT4の解説

  • BF16
  • データ型
  • ディープラーニング
  • 浮動小数点
  • FP16
  • FP32
  • GPU Memory
  • 推論最適化
  • INT8
  • モデル圧縮
  • モデル精度
  • 訓練最適化
  • Wasif Mehmood
  • Ready Tensor
  • Mohamed Abdelhamid

🏠
ホーム – 全てのレッスン

⬅️
前へ – LLMにおける命令ファインチューニング

➡️
次へ – 量子化とダブル量子化

これは小さな詳細のように聞こえるかもしれませんが、データ型の選択によって、モデルの訓練速度、メモリ消費量、さらには安定性までが決まります。

このレッスンでは、FP32、FP16、BF16、INT8、INT4といった形式が実際に何を意味するのか、精度とパフォーマンスのトレードオフ、そして現代のLLMがなぜ1つの形式だけに固執しないのかを解き明かします。

最後には、訓練、ファインチューニング、推論のどのシーンでどのデータ型を使用すべきか、そして精度の決定が大規模モデルのパフォーマンスを左右する理由を正確に理解できるようになります。

データ型が重要な理由

あなたが訓練するすべてのモデル — 1Bパラメータの LLaMA バリアントであろうと、70Bの巨大モデルであろうと — は、膨大な数値の集合にすぎません。
それらの数値にはそれぞれ形式があります: 32ビット、16ビット、あるいは4ビットです。

このシンプルな選択が、すべてに影響します:
必要なGPUメモリ量、モデルの実行速度、そして勾配と重みをどれだけ正確に表現できるか。

これらの形式が実際に何を意味するのか解き明かしていきましょう。

浮動小数点データ型の解説

まずは、訓練やファインチューニング中に遭遇するデータ型から始めましょう: 浮動小数点型です。

すべての浮動小数点数は3つの部分から構成されています:

  • 符号ビット — 数値が正か負か?
  • 指数部 — 数値はどれだけ大きいまたは小さいか? (範囲を制御)
  • 仮数部 (または有効数字) — 実際の桁は何か? (精度を制御)

科学的記数法のようなものと考えてください。3.14 × 10² という数値は:

3.14 × 10²
– 符号 (正)
– 指数部 (10² = 100)
10²
– 仮数部 (3.14)
3.14

同じ構造がコンピュータが小数を保存する方法にも適用されますが、すべてが二進法で表現されます。

重要な洞察: すべての浮動小数点形式は、範囲 (数値がどれだけ大きいまたは小さくなれるか) と精度 (どれだけ正確に表現できるか) の間でトレードオフを行います。

FP32、FP16、BF16がどのように異なるトレードオフを行うか見ていきましょう。

ビデオウォークスルー: PyTorchでのFP32、FP16、BF16の理解

このビデオでは、浮動小数点データ型がモデルの精度とメモリにどのように影響するかを学び、PyTorchでFP32、FP16、BF16テンソルを比較する実際の計算を見ることができます。

FP32 (Float32) — フル精度ベースライン

FP32はディープラーニングの伝統的な標準です。各数値を保存するために32ビットを使用します:

  • 符号ビット: 1ビット
  • 指数部: 8ビット
  • 仮数部: 23ビット

これにより得られるもの:

  • 範囲: ±3.4 × 10³⁸ (非常に広い)
  • 精度: 約7-8桁の10進数

FP32は最も安定しています。勾配のオーバーフローやアンダーフローが発生しにくく、丸め誤差も最小限に抑えられます。小さなモデルや最大精度が必要な研究実験では、FP32が今でも選ばれる選択肢です。

しかし、落とし穴があります: コストがかかるのです。

8ビットで1バイトなので、FP32の値はメモリ内で4バイトを占有します。

70億パラメータのモデルをFP32で保存すると、重みだけで28GBのメモリを消費します。勾配、オプティマイザ状態、訓練中の活性化を加えると、簡単に50GB以上になります。これはほとんどのGPUには収まりません。

したがって、FP32が最も安全な選択肢である一方、現代のワークフローではそれだけを使用することはほとんどありません。

FP16 (Float16) – 半精度

FP16はビット数を半分にカットします: 合計16ビットです。

  • 指数部: 5ビット
  • 仮数部: 10ビット
  • 範囲: ±65,504 (FP32よりはるかに小さい!)
  • 精度: 約3-4桁の10進数

即座のメリットは? メモリが半分になります。7BモデルのFP16は28GBではなく、わずか14GBです。

現代のGPUには専用ハードウェア (NVIDIAのTensor Coreなど) があり、FP16演算に最適化されており、行列演算をFP32よりも高速に実行できます。

しかし、FP16には問題があります: 範囲がはるかに狭いのです。

訓練中、勾配は簡単に65,504を超えたり、最小表現可能数を下回ったりし、オーバーフローまたはアンダーフローを引き起こします。これが起こると、訓練が不安定になるか、完全に壊れてしまいます。

これを回避するために、エンジニアは損失スケーリングという技術を使用します: バックプロパゲーション前に勾配を大きな定数で掛け、その後スケールを戻します。これは機能しますが、複雑さの層を追加します。

FP16は推論 (安定性がそれほど重要でない場合) や混合精度訓練 (後述) には優れていますが、純粋な訓練ワークフローには、より良い選択肢があります。

BF16 (BFloat16) – 現代の標準

BF16はディープラーニング専用にGoogleによって設計されました。FP16と同様に16ビットを使用しますが、それらを異なる方法で割り当てます:

  • 指数部: 8ビット (FP32と同じ!)
  • 仮数部: 7ビット
  • 範囲: ±3.4 × 10³⁸ (FP32と同じ)
  • 精度: 約2-3桁の10進数

ここに重要な洞察があります: BF16は精度を犠牲にしてFP32の範囲を維持します。

指数部にFP32と同じ8ビットを与えることで、BF16は同じ巨大な値の範囲を表現できます。これは、訓練中でも勾配がほとんどオーバーフローまたはアンダーフローしないことを意味し、損失スケーリングは不要です。

はい、BF16はFP16よりも精度が低いです。しかし実際には、ニューラルネットワークはその余分な精度を必要としません。小さな丸め誤差に対して頑健なのです。彼らが必要とするのは安定性であり、BF16はそれを提供します。

BF16は現在、現代のLLMのデフォルト訓練形式です。次のハードウェアでサポートされています:

  • GoogleのTPU (発明された場所)
  • NVIDIA GPU (A100、H100)
  • AMDのMI250アクセラレータ

今日大きなモデルを訓練またはファインチューニングしている場合、ほぼ確実にBF16を使用しています。

FP8 – 新興標準

NVIDIAのH100 GPUなどの最先端ハードウェアに登場し始めているFP8 (8ビット浮動小数点) という新しい形式があります。これはFP16とINT8の間に位置し、さらに少ないメモリで浮動小数点表現を提供します。有望ですが、標準ワークフローではまだ広く採用されていません。

推論のための整数データ型

次に、効率的な推論のために整数形式がどのように使用されるかを見ていきましょう。

モデルがすでに訓練されている場合、それを実行するために常に完全な浮動小数点精度が必要というわけではありません。整数表現は重みをコンパクトに保存し、わずかな精度のトレードオフで操作をより速く実行できます。

INT8 – 効率的で信頼性が高い

INT8は各数値を8ビット整数として保存します — 指数部も仮数部もなく、単なる整数です。

符号付きINT8値は-128から+127までの数値を表現でき、符号なしの場合は0から255までです。

つまり、0.00341や-12.8457のような小数を直接表現する方法はなく、整数のみです。

0.00341
-12.8457

では、浮動小数点モデルの重みを保存するために整数をどのように使用するのでしょうか?

答えは量子化です: 連続した浮動小数点値をこの限定された整数範囲にマッピングし、推論中にそれらを再スケールするスケーリングプロセスです。

次のセクションで、それがどのように機能するかを正確に探ります。

INT4 – 極端な圧縮

INT4はこれをさらに進めます。1つの数値につきわずか4ビットを使用します:

4ビット符号付き整数は-8から+7までの値を表現できます。
4ビット符号なし整数は0から15までの値を表現できます。

これは非常に狭い範囲です。しかし、慎重な量子化により、まだ使用可能な結果を得ることができます。

INT4は特にQLoRA (Quantized Low-Rank Adaptation) のような技術で人気があり、ベースモデルを4ビットに圧縮しながら訓練可能なアダプタをより高い精度で保持することで、コンシューマーGPU上で大規模モデルのファインチューニングを可能にします。

NF4 (NormalFloat-4) – ニューラルネットワーク最適化4ビット

標準のINT4は、その16個の離散値を範囲全体に均等に分散させます (例: -8から+7)。

しかし、ニューラルネットワークの重みは均等に分布していません—ゼロ周辺にクラスタ化され、
おおよそ正規 (ガウス) 分布になります。

NF4は、ほとんどの表現可能な値をゼロ付近 (ほとんどのニューラルネットワークの重みがある場所) に配置し、
極端な部分には少なく配置する特殊な4ビット形式です。これにより、
均一な4ビット量子化よりもはるかに優れたモデル品質を保持します。

主な特徴:

  • INT4と同じ4ビットを使用
  • 値は不均等に配置 (ゼロ付近でより高い解像度)
  • 特に事前訓練済みモデルの重みを量子化するために設計

NF4は、ベースモデルの重みを保存するためにQLoRAで使用される形式です。
次のレッスンで、量子化とダブル量子化がそれを使用して大規模モデルを効率的に圧縮する方法を実際に見ることができます。

比較表 – データ型のまとめ

ビデオウォークスルー: モデルメモリ要件の計算

このビデオでは、パラメータ数とデータ型に基づいてモデルが必要とするGPUメモリを推定する方法を学び、FP32からINT4への変更がメモリを最大8倍削減する方法を確認します。

メモリ要件 — 実践的な計算

データ型を理解したので、本当に重要なことについて話しましょう: モデルは実際にどれだけのメモリを必要とするのでしょうか?

式はシンプルです:

メモリ (バイト単位) = パラメータ数 × パラメータあたりのバイト数

例えば:

  • FP32の70億パラメータモデルは: 7B × 4バイト = 28GB を使用
    7B × 4バイト = 28GB
  • BF16での同じモデルは: 7B × 2バイト = 14GB を使用
    7B × 2バイト = 14GB
  • INT8の場合: 7B × 1バイト = 7GB
    7B × 1バイト = 7GB
  • INT4の場合: 7B × 0.5バイト = 3.5GB
    7B × 0.5バイト = 3.5GB

これを表にまとめましょう:

これは重みを保存するためだけのものです。訓練中には、次のためのメモリも必要です:

  • 勾配 (重みと同じサイズ)
  • オプティマイザ状態 (Adamの場合、重みサイズの2倍になることが多い)
  • 活性化 (バッチサイズとシーケンス長に依存)

したがって、訓練メモリは簡単にモデルサイズの3-4倍以上になります。

まとめと重要なポイント

データ型は、GPUコストからモデルの安定性まで、すべてを支配する静かなエンジニアリング決定です。

チートシートは次のとおりです:

これらの精度形式を理解することで、精度、安定性、効率性の間の適切なバランスを選択できるようになり、次に取り上げる量子化のような圧縮技術の準備が整います。

  • ディープラーニングにおけるデータ型の重要性

コメント

タイトルとURLをコピーしました