
Gemma 4 の NVFP4 も 2 つの量子化版を DGX Spark で比べてみた
はじめに
こんにちは、クラスメソッド製造ビジネステクノロジー部の森茂です。
先日 Qwen3.6-35B-A3B の量子化版対決を書いたばかりなのですが、今度は Unsloth が Gemma 4 の全系列(E2B から 31B まで)の Dynamic NVFP4 quants を公開して話題になっています。Qwen のときは「2.5 倍速い」の看板に対して実測では NVIDIA 版が全勝、という決着でした。では Gemma 4 でも同じ構図になるのか。気になっている方も多いのではないでしょうか。
自分にはもうひとつ、この対決をやっておきたい事情がありました。7 月頭の記事で Gemma 4 26B-A4B を実測したとき、自分の環境では 30 tok/s だったのに、海外の検証ブログでは 52 tok/s という報告があり、この 1.7 倍の乖離が説明できないまま宿題になっていたのです。両方の量子化版を同じ条件で測れば、この謎にも決着がつくはずです。
先に結論を書いておくと、今度は Unsloth 版の全勝でした。26B-A4B で NVIDIA 版の 31.6 tok/s に対し Unsloth 版は 49.1 tok/s と 55% 速く、品質チェックは両版とも全問クリア。例の「30 vs 52」の乖離は、backend でもビルドでもなく量子化形式の違いでほぼ説明がつきました。さらに、7 月上旬から全ビルドで壊れていた外部 drafter の投機デコードも issue で見つけた回避策で復活し、Unsloth 版 26B は drafter 込みで 68.8 tok/s、置物扱いだった 31B も 20.8 tok/s まで伸びています。vLLM の新しい stable v0.25.1 で「Gemma 4 の NVFP4 は nightly 必須」という制約が終わっていたことも確認できました。
前提になる記事はこちらの 2 本です(2026-07-06 / 2026-07-13 公開時点の記事です)。計測条件はどちらとも揃えてあります。
この記事では、Gemma 4 の 26B-A4B と 31B それぞれについて NVIDIA 版と Unsloth 版の NVFP4 を DGX Spark 単体で実測し、速度・品質・画像入力から投機デコードの復活まで横断で確認した結果を紹介します。DGX Spark で Gemma 4 を動かしている人、量子化版の選び方に迷っている人に刺さるといいなと思っています。
Gemma 4 の NVFP4 も 2 系統ある
Qwen のときと同じく、Gemma 4 の NVFP4 も配布元が 2 つあり、量子化の方式そのものが違います。
| 項目 | NVIDIA 版 | Unsloth 版 |
|---|---|---|
| HF リポジトリ | nvidia/Gemma-4-26B-A4B-NVFP4 ほか | unsloth/gemma-4-26B-A4B-it-NVFP4 ほか |
| 量子化方式 | modelopt(static PTQ) | compressed-tensors(Dynamic 2.0) |
| calibration | CNN/DailyMail 30 万記事 | コーディング・tool calling・チャット + UltraChat |
| 中身 | 重み + 活性化を NVFP4 に一括変換 | 重要層を FP8/BF16 で温存し、残りを W4A4 |
| キャッシュ実測 | 26B 約 18GB / 31B 約 31GB | 26B 約 16GB / 31B 約 24GB |
面白いのは、Qwen 35B-A3B ではチェックポイントが大きかった Unsloth 版が、Gemma 4 では NVIDIA 版より小さいことです。ダウンロードして config.json を見ると quant_method は compressed-tensors の mixed-precision で、Qwen のときと同じ作りでした。
Unsloth の公称は 26B-A4B で 1.41 倍、31B で 1.45 倍です。ただしこの数字は 1 台の B200 に 128 並列をかけたときの throughput の BF16 比なので、DGX Spark の単一セッションにそのまま当てはまる保証はありません。Qwen のときは実際に当てはまりませんでした。今回も同じハーネスで、素の実力を測っていきます。
vLLM v0.25.1
Unsloth 版は compressed-tensors を vLLM が自動認識するので、NVIDIA 版で使う --quantization modelopt を外すだけです。
vllm serve unsloth/gemma-4-26B-A4B-it-NVFP4 \
--host 0.0.0.0 --port 8000 \
--kv-cache-dtype fp8 \
--max-model-len 65536 \
--max-num-seqs 8 \
--max-num-batched-tokens 4096 \
--gpu-memory-utilization 0.85 \
--reasoning-parser gemma4 \
--enable-prefix-caching --trust-remote-code
backend の指定はどれを選んでも変わらなかった
ここで以前うまく結果が出せなかった「30 vs 52」に取りかかります。まず疑ったのは MoE backend の違いでした。52 tok/s を報告していた検証は --moe-backend marlin を指定しており、自分の 30 tok/s のログは flashinfer_cutlass を使っていたからです。NVIDIA 版 26B-A4B で backend を 4 通り振って、単一セッションの decode 速度を測りました。
| moe-backend 指定 | single tok/s |
|---|---|
| 指定なし(auto) | 30.91 |
| marlin | 31.28 |
| flashinfer_cutlass | 30.85 |
| flashinfer_b12x | 起動不可 |
上 3 つの差は 1.4% で誤差です。つまり backend 説は外れでした。起動ログを見ると auto は内部で FLASHINFER_CUTLASS を選んでいて、どれを選んでも同じ土俵に乗るだけのようです。
Unsloth のドキュメントは DGX Spark 向けに「--moe-backend flashinfer_b12x を必ず使え、さもないと 2 倍遅い」と書いているのですが、指定すると起動できません。
ValueError: NvFp4 MoE backend 'FLASHINFER_B12X' does not support the deployment
configuration since kernel does not support MoEActivation.GELU_TANH activation.
Gemma 4 の MoE は活性化関数に GELU-tanh を使っていて、b12x カーネルがこれに対応していないためです。Qwen 35B のときは「効いても誤差 1.5%」でしたが、Gemma 4 に至っては土俵に上がることすらできませんでした。あわせて推奨されている環境変数 CUTE_DSL_ARCH=sm_121a も勝者構成で前後比較しましたが、47.98 tok/s と誤差の範囲でした。少なくとも公式の vLLM イメージを使うかぎり、Unsloth の DGX Spark 向け推奨フラグは 2 つとも気にしなくてよさそうです。
26B-A4B 対決は Unsloth 版の完勝だった
backend でないなら、残る容疑者は量子化形式そのものです。同じ vLLM v0.25.1、同じ auto backend、同じハーネスで両版を測りました。計測は前 2 記事とまったく同じで、256 トークンを強制生成して TTFT を除いた decode 速度を取り、single は 3 回の中央値、並列は同時リクエストの合計値を見ます。

青が NVIDIA 版(modelopt)、緑が Unsloth 版(compressed-tensors)。Qwen 35B-A3B の対決とは勝敗が入れ替わった。
| 構成 | NVIDIA 版 | Unsloth 版 | 差 |
|---|---|---|---|
| single | 31.63 | 49.13 | +55.3% |
| 2 並列(合計) | 60.0 | 80.4 | +33.9% |
| 4 並列(合計) | 119.7 | 156.2 | +30.5% |
| 8 並列(合計) | 207.7 | 262.9 | +26.6% |
single で 55% 差、8 並列でも 27% 差と、全域で Unsloth 版の完勝です。Qwen 35B-A3B では NVIDIA 版が全構成で 12〜17% 勝っていたので、量子化版の優劣がモデルによってそっくり入れ替わったことになります。
そして「30 vs 52」の答え合わせです。NVIDIA 版の 31.6 は自分が 7 月頭に測った 30.19 と整合し、Unsloth 版の 49.1 は例の 52 tok/s 報告にかなり近い。少なくとも自分の環境では、backend を 4 通り入れ替えても 31 が上限だったのに、量子化形式を変えただけで 49 に届きました。1.7 倍の乖離の正体は、modelopt の世界と compressed-tensors の世界の違いだったと見てよさそうです。
なぜ Gemma 4 では逆転するのか。確定的なことは言えませんが、状況証拠は活性化関数を指しています。b12x カーネルが GELU-tanh 未対応で弾かれたように、Gemma 4 の MoE は Qwen 系とは違う演算パターンを持っていて、modelopt 版が乗れる最適カーネルの選択肢が狭い。一方 compressed-tensors 版は重要層を FP8/BF16 で残す構成が、結果的にこのモデルの形と相性がよかった。量子化形式は「どちらが優れているか」ではなく「モデルごとにどちらが合うか」で選ぶもの、というのが 2 回の対決から見えてきた教訓です。
31B の対決も Unsloth 版、ただし土俵が違う
dense 31B でも同じ構図を確認しました。single で NVIDIA 版 7.05 に対し Unsloth 版 8.97 と 27% 速く、8 並列の合計でも 71.3 対 55.1 で Unsloth 版が上です。勝敗だけ見れば 26B-A4B と同じです。
ただ、絶対値を見ると話が変わります。毎トークン 30.7B ぶんの重みを読む dense モデルは、メモリ帯域 273 GB/s の DGX Spark では 1 桁 tok/s が定位置で、量子化版を選び直しても 2 桁の入り口に届くかどうか。前々回の記事で立てた「decode 速度は 1 トークンで読むバイト量で決まる」という見立てのとおりです。もっとも、この 31B は次の投機デコードで表情が変わるので、見限るのはまだ早いです。
壊れていた MTP は回避策で蘇った
Gemma 4 の楽しみといえば、投機デコードで decode を倍速にする外部 drafter(gemma-4-XXB-it-assistant)です。7 月頭の検証では 26B-A4B に 832MB の drafter を付けて 30.19 から 62.36 tok/s、2.07 倍を実測していました。ところが今回、そのまま drafter を付けると v0.25.1 でも最新 nightly でも起動できません。torch compile の段階で次のエラーになります。
RuntimeError: a and b must have same reduction dim, but got [s47, 3840] X [5632, 1024].
Gemma 4 の drafter は、target 側の embedding を借りて hidden state と連結した 5632 次元の入力を受け取る設計です。ところが 7 月上旬に入った別モデル向けの修正が「target と drafter で embedding の幅が違う場合は共有を禁止する」ガードを追加したため、drafter が自前の embedding を使うようになり、連結後の入力が 3840 次元のまま射影層の期待する 5632 と噛み合わなくなりました。手元で drafter の重みを覗くと pre_projection が [1024, 5632] で、エラーの数字とぴったり一致します。
調べてみると、vLLM には既に同症状の issue が 2 本上がっていて(#47794、#48848。後者は同じ DGX Spark ユーザーからの報告です)、原因コミットの特定も修正 PR も進行中でした。そして #48848 のコメント欄に、救いの一言がありました。環境変数 VLLM_USE_V2_MODEL_RUNNER=1 で新しい実行系に切り替えると、このクラッシュを踏まずに済むというのです。
試してみると、本当に動きました。stable v0.25.1 のまま drafter が起動し、投機デコードのカウンタも健全に回ります。V2 runner 自体の影響は、素の 26B で前後比較して -3.9% と誤差に近い範囲でした。というわけで、止まっていた MTP 対決を回避策の上で全部やり直した結果がこちらです。
| 構成 | 素 single | + drafter single | 倍率 | 最適 spec |
|---|---|---|---|---|
| 26B-A4B(NVIDIA 版) | 31.63 | 60.31 | 1.91x | 2 |
| 26B-A4B(Unsloth 版) | 49.13 | 68.78 | 1.40x | 2 |
| 31B(NVIDIA 版) | 7.05 | 19.42 | 2.75x | 4 |
| 31B(Unsloth 版) | 8.97 | 20.77 | 2.32x | 4 |
注目する点は 3 つ。1 つ目、drafter 込みでも Unsloth 版の全勝は崩れませんでした。26B-A4B の 68.8 tok/s は、単体ランキングで Nemotron Nano を抜いて王者 Qwen 35B-A3B に次ぐ 2 位です。
2 つ目、投機の倍率は base が速いほど薄まりました。NVIDIA 版が 1.91 倍伸びるのに対し、Unsloth 版は 1.40 倍止まり。drafter の予測品質は同じでも、target の 1 ステップが速いほど検証コストの相対比重が上がるので、これは投機デコードの宿命です。「速い量子化版ほど MTP の恩恵は小さい」は覚えておいて損がない性質だと思います。
3 つ目は 31B の大逆転です。素では 1 桁 tok/s で置物扱いだった dense 31B が、drafter を付けると 20 tok/s 台に乗ってきました。しかも 26B では効果がなかった先読み 4(spec=4)が 31B でははっきり効きます。Google が 31B 用 drafter に推奨する num_speculative_tokens 4〜8 は、少なくとも 4 までは DGX Spark でも正しいという裏付けが取れました。1 ステップが遅いモデルほど投機が効く、の好例ですね。
ひとつ注意点があります。V2 runner は開発中の実行系への切り替えであり、正規の修正ではありません。修正 PR がマージされるまでのつなぎとして使うのが正しい距離感です。なお issue のスレッドでは別ハードウェアからの追認も続いていて、性能は V1 と誤差内という報告で揃っています。起動後の初回だけ並列リクエスト時の TTFT が数百 ms 引っかかる warmup 挙動も報告されているので、レイテンシに敏感な用途では頭の隅に置いておくとよさそうです。
品質と画像入力も見ておく
速度差が量子化の雑さから来ていたら本末転倒なので、前 2 記事と同じ日本語の品質チェック 4 問(50 文字以内の指示遵守、自由記述、コード生成、数値計算)を 4 構成すべてに通しました。
結果は、drafter 付きの構成まで含めた全構成で全問クリアです。「日本の首都について句読点含め 50 文字以内で」に NVIDIA 版 26B が 37 文字、Unsloth 版 26B が 45 文字で収め、コード生成は実行検証まで正解、リンゴとみかんの計算も両版とも合っています。Gemma 4 は thinking を長々と回さないぶん、この手の指示遵守はもともと得意で、量子化版や実行系を替えてもその性格は崩れませんでした。
画像入力も確認しました。投機デコードを有効にしたまま赤い円と青い四角のテスト画像を投げると、両版とも spec デコードが生きたまま正しく応答し、Unsloth 版はテキスト 69.0 tok/s に対して画像で 71.7〜87.7 tok/s が出ています。drafter はテキスト専用に退避しつつ本体の VL は保たれる、という 7 月頭に確認した挙動が回避策の上でも維持されている形です。

Gemma 4 対決後の DGX Spark 単体ランキング。Gemma の 3 本(★今回)は素が v0.25.1、MTP 上乗せは回避策(V2 runner)込みの実測。他は前 2 記事の実測。
まとめ
Gemma 4 の NVFP4 量子化版対決、答えは Qwen と真逆でした。26B-A4B は Unsloth 版が single 49.1 tok/s で 55% 速く、31B も Unsloth 版が上。品質は両版とも全問クリアなので、DGX Spark で Gemma 4 26B-A4B を使うなら、現時点では Unsloth 版を選ばない理由が見当たりません。7 月頭から宿題になっていた 30 vs 52 の乖離も、量子化形式の違いということで自分の中では決着です。
同時に、この 2 連戦で「NVFP4 は配布元で選ばず、モデルごとに実測して選ぶ」という身も蓋もない結論も固まりました。Qwen 35B-A3B は NVIDIA 版、Gemma 4 は Unsloth 版。公称の倍率はどちらも B200 の並列 throughput の話で、DGX Spark の単一セッションの体感を語ってくれません。1 台のパートナー枠は依然として Qwen3.6-35B-A3B の 108 tok/s が王者ですが、Unsloth 版 Gemma 26B-A4B が drafter 込み 68.8 tok/s で単体 2 位に浮上しました。指示遵守と画像入力に強い 2 番手として、王者と使い分ける構成が現実味を帯びてきています。
参考リンク
- Run Unsloth Dynamic NVFP4 Guide | Unsloth Documentation
- unsloth/gemma-4-26B-A4B-it-NVFP4
- unsloth/gemma-4-31B-it-NVFP4
- nvidia/Gemma-4-26B-A4B-NVFP4
- nvidia/Gemma-4-31B-IT-NVFP4
- google/gemma-4-26B-A4B-it-assistant — 外部 drafter(現行ビルドでは起動不可)
- vLLM Releases — v0.25.0 に Gemma4 の tied embeddings 修正
- vLLM Issue #47794 — drafter 回帰の原因特定(embedding 共有ガード)
- vLLM Issue #48848 — v0.25.1 での同症状報告(DGX Spark)。回避策もこのスレッド発
- MiaAI-Lab/Gemma-4-31B-IT-NVFP4-Recipe — 31B を 262K フルコンテキストで使う長文特化レシピ。drafter は spec=4 で本記事の実測と一致(drafter 起動には本記事の回避策が必要な点に注意)
- Gemma 4 26B-A4B on DGX Spark: 52 tok/s with NVFP4 — ai-muninn(「30 vs 52」の 52 側の報告)
- Accelerating Gemma 4: faster inference with multi-token prediction drafters — Google







