🐈
GGUFファイルの量子化タイプについて
はじめに
llama.cppは独自の量子化アルゴリズムを使用している。公式でまとまった資料がないため、PRやIssueを追わないといけないっぽい。
以下の記述はReddit post[1]の内容をもとに、関連するPR/Issueを辿って詳細を補足したもの。
用語について
- GGUFはファイルフォーマットの名称であって、量子化アルゴリズムを指すものではない
- GGMLはllama.cppの計算ライブラリをさす名称のようだが、issueでは"In the existing ggml quantization types"という使われ方をしていて、
GGML
は仕様の名称としても使われてるっぽい。 - この記事では無難に「llama.cppの量子化アルゴリズム」と呼ぶことにする
llama.cppの量子化アルゴリズム
Legacy quants: 固定ビットレート
-
QX_[0-4]
という名前がついたもの(例: Q4_0, Q4_1, Q8_0, ...) - weightの区画(block)ごとに異なるスケールを適用してquantize/dequantizeする。
-
f
を量子化関数、q
を量子化時のモデルの重み、x
を計算時のモデル重み、d
をスケールとすると、quantizeはq = f(x / d)
、dequantizeはx=d * q
と計算される。 - 従って圧縮後は量子化された重み+スケール(or バイアス)パラメータを保持する。
_[0-4]の定義
q->xにdequantizeするときのバイアスの有無とblockサイズ(独立してスケールするweightの区画のサイズ)が異なる。
- 0: バイアスなし(
x = d * q
)。block=32 - 1: バイアスあり(
x = m + d * q
)。block=32 - 2: バイアスなし(
x = d * q
)。block=16 - 3: バイアスあり(
x = m + d * q
)。block=16 - 4: バイアスなし(
x = d * q
)。block=8, super block=16
super blockについて
PPLによる評価ではblock=32よりblock=16の方が性能が良かった。従って、スケールする粒度(block数)を小さくするほど性能がよくなると考えられるが、block=8を採用した場合、スケール分に一律にFP16を確保すると圧縮効率が悪い(例: 4 bit量子化の場合、bit rate=4 + 16/8=6 bpw)。そこで、_4
以降では
- blockごとのスケールはINT8で保持
- blockをまとめたsuper blockで共通のスケールをFP16で保持
という2段階のスケーリングを採用した。この方式により、量子化ビット数4, block=8, super block=16でのビットレートは5.125 bpw (4 + 8/8 + 16/(16*8))となる。
K-quants: 可変ビットレート
-
QX_K_{S,M,L}
という名前がついたもの(Q3_K_S, Q5_K_M, ...) - 均一のビットレートで量子化よりも、レイヤごとに精度を変えた方が同じ圧縮率でPPLが低くできる(例: 4bit → 3bit + 5bit)という実験結果に基づき、レイヤごとに異なる精度で量子化している。
- 最初、
QX
は量子化ビット数を表していたが、この方式だと異なる精度が混ざっているのでビットレート(weightあたりの平均量子化ビット数)を表すようになった - レイヤごとのビット数の混合の配分によってビットレート(の小数点以下)が異なる。混合の配分のプリセットにはそれぞれS, M, Lなどの名称がついていて、S<M<Lの順にビットレートが大きくPPLが小さい(性能が良い)
-
_4
と同様にsuper blockを採用している
参考: k-quants #1684
I-quants
-
IQX_{XXS,XS,S,...}
という名前のもの (IQ2_XXS, IQ3_S, ...) - SOTAの2 bit量子化アルゴリズムQuIP#[2]のアイデアの一部を取り入れた
Even more quants?
将来的な量子化アルゴリズムの可能性について議論されている。
- Row-wise quantization
- Non-linear quantization
- k-means clustering quantization
参考: Even more quantization types? #5063
1.5Bit量子化
1.5bit量子化も実用化されている。
最近だとunslothがDeepSeek-R1の1.5bit量子化したGGUFを公開した[3]のが有名。
IQ1_S
- PPL PB-LLM, PPL BiLLMを参考にしつつ、これらを上回る性能(PPL)を実現
- salient/non-salient channelの分離に1bit使うので、channelの分離は不採用
IQ1_S_R4
- superblockを採用せず、block=32に(R1は256で割り切れないチャネルが多かったため)
参考: IQ1_S_R4: better 1.5bpw quantization
Discussion
参考: 2023年末のTuringの資料ではデータの持ち方まで詳細にリバースエンジニアリングされている。