<?xml version="1.0" encoding="utf-8" standalone="yes"?><rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:content="http://purl.org/rss/1.0/modules/content/"><channel><title>Quantization on Tarragon</title><link>https://tarrragon.github.io/blog/tags/quantization/</link><description>Recent content in Quantization on Tarragon</description><generator>Hugo -- gohugo.io</generator><language>zh-TW</language><copyright>Tarragon (CC BY 4.0)</copyright><lastBuildDate>Tue, 12 May 2026 00:00:00 +0000</lastBuildDate><atom:link href="https://tarrragon.github.io/blog/tags/quantization/index.xml" rel="self" type="application/rss+xml"/><item><title>QLoRA</title><link>https://tarrragon.github.io/blog/llm/knowledge-cards/qlora/</link><pubDate>Tue, 12 May 2026 00:00:00 +0000</pubDate><guid>https://tarrragon.github.io/blog/llm/knowledge-cards/qlora/</guid><description>&lt;p>QLoRA（Quantized LoRA、Dettmers et al., 2023）的核心概念是「&lt;strong>把 base model 量化到 4-bit（凍住）+ 用 &lt;a href="https://tarrragon.github.io/blog/llm/knowledge-cards/lora/" data-link-title="LoRA" data-link-desc="Low-Rank Adaptation：凍住原模型權重、只訓兩個小矩陣的 parameter-efficient fine-tuning">LoRA&lt;/a> 訓兩個小矩陣&lt;/strong>」。讓消費級 GPU（24GB VRAM）就能 fine-tune 30B-70B 模型、是現代 local fine-tuning 主流。&lt;/p>
&lt;h2 id="概念位置">概念位置&lt;/h2>
&lt;p>QLoRA vs full fine-tuning vs LoRA 的記憶體需求對比（70B 模型）：&lt;/p>
&lt;table>
 &lt;thead>
 &lt;tr>
 &lt;th>方法&lt;/th>
 &lt;th>Base model 精度&lt;/th>
 &lt;th>訓練記憶體&lt;/th>
 &lt;th>適合硬體&lt;/th>
 &lt;/tr>
 &lt;/thead>
 &lt;tbody>
 &lt;tr>
 &lt;td>Full fine-tuning&lt;/td>
 &lt;td>BF16&lt;/td>
 &lt;td>~280 GB&lt;/td>
 &lt;td>多卡 H100&lt;/td>
 &lt;/tr>
 &lt;tr>
 &lt;td>LoRA&lt;/td>
 &lt;td>BF16&lt;/td>
 &lt;td>~150 GB&lt;/td>
 &lt;td>多卡 A100 / H100&lt;/td>
 &lt;/tr>
 &lt;tr>
 &lt;td>&lt;strong>QLoRA&lt;/strong>&lt;/td>
 &lt;td>4-bit (NF4)&lt;/td>
 &lt;td>&lt;strong>~40 GB&lt;/strong>&lt;/td>
 &lt;td>單張 A100 80GB / 雙 24GB GPU&lt;/td>
 &lt;/tr>
 &lt;tr>
 &lt;td>QLoRA on 7B&lt;/td>
 &lt;td>4-bit&lt;/td>
 &lt;td>~6-8 GB&lt;/td>
 &lt;td>消費級 16GB+ GPU&lt;/td>
 &lt;/tr>
 &lt;tr>
 &lt;td>QLoRA on 30-32B&lt;/td>
 &lt;td>4-bit&lt;/td>
 &lt;td>~20-24 GB&lt;/td>
 &lt;td>消費級 24GB+ GPU（5090）&lt;/td>
 &lt;/tr>
 &lt;/tbody>
&lt;/table>
&lt;p>QLoRA 的核心創新（簡化）：&lt;/p>
&lt;ol>
&lt;li>&lt;strong>4-bit NormalFloat（NF4）量化&lt;/strong>：base model 用 4-bit 表示、精度損失低於原 INT4&lt;/li>
&lt;li>&lt;strong>Double quantization&lt;/strong>：量化常數本身也量化、再省一點記憶體&lt;/li>
&lt;li>&lt;strong>Paged optimizer&lt;/strong>：optimizer state 跑 CPU offload、避免訓練 spike OOM&lt;/li>
&lt;li>&lt;strong>LoRA on 4-bit base&lt;/strong>：&lt;a href="https://tarrragon.github.io/blog/llm/knowledge-cards/lora/" data-link-title="LoRA" data-link-desc="Low-Rank Adaptation：凍住原模型權重、只訓兩個小矩陣的 parameter-efficient fine-tuning">LoRA&lt;/a> 訓的 A、B 矩陣仍是 BF16、只有 base 是 4-bit、推論時 dequantize → 加 LoRA → forward&lt;/li>
&lt;/ol>
&lt;h2 id="設計責任">設計責任&lt;/h2>
&lt;p>讀 fine-tuning 教學 / Hugging Face PEFT 文件看到「QLoRA」「bnb-4bit」就是這方法。寫 code 場景的判讀：&lt;/p>
&lt;ol>
&lt;li>&lt;strong>想 fine-tune 大模型在消費級硬體&lt;/strong>：QLoRA 是 default 選擇（不用 QLoRA、就只能訓 &amp;lt; 7B）&lt;/li>
&lt;li>&lt;strong>記憶體預算估算&lt;/strong>：QLoRA 訓 N B 模型約需 &lt;code>0.6 × N GB&lt;/code> VRAM（30B → ~18GB、70B → ~42GB）&lt;/li>
&lt;li>&lt;strong>品質 vs full fine-tune 差距&lt;/strong>：QLoRA 後合併權重的模型、實測跟 full fine-tune 接近（差距 &amp;lt; 2-3%）、對多數場景可接受&lt;/li>
&lt;li>&lt;strong>跟 &lt;a href="https://tarrragon.github.io/blog/llm/knowledge-cards/lora/" data-link-title="LoRA" data-link-desc="Low-Rank Adaptation：凍住原模型權重、只訓兩個小矩陣的 parameter-efficient fine-tuning">LoRA&lt;/a> 卡片區分&lt;/strong>：純 LoRA 是「base 不量化、訓 LoRA」、QLoRA 是「base 量化 4-bit、訓 LoRA」；QLoRA 是 LoRA 的延伸、不是替代&lt;/li>
&lt;li>&lt;strong>推論時的選擇&lt;/strong>：QLoRA fine-tuned 模型可以「base 仍 4-bit + 載入 LoRA adapter」推論、記憶體用量低；也可以 merge 後用 GGUF Q4_K_M、跟 base 原相同&lt;/li>
&lt;/ol></description><content:encoded><![CDATA[<p>QLoRA（Quantized LoRA、Dettmers et al., 2023）的核心概念是「<strong>把 base model 量化到 4-bit（凍住）+ 用 <a href="/blog/llm/knowledge-cards/lora/" data-link-title="LoRA" data-link-desc="Low-Rank Adaptation：凍住原模型權重、只訓兩個小矩陣的 parameter-efficient fine-tuning">LoRA</a> 訓兩個小矩陣</strong>」。讓消費級 GPU（24GB VRAM）就能 fine-tune 30B-70B 模型、是現代 local fine-tuning 主流。</p>
<h2 id="概念位置">概念位置</h2>
<p>QLoRA vs full fine-tuning vs LoRA 的記憶體需求對比（70B 模型）：</p>
<table>
  <thead>
      <tr>
          <th>方法</th>
          <th>Base model 精度</th>
          <th>訓練記憶體</th>
          <th>適合硬體</th>
      </tr>
  </thead>
  <tbody>
      <tr>
          <td>Full fine-tuning</td>
          <td>BF16</td>
          <td>~280 GB</td>
          <td>多卡 H100</td>
      </tr>
      <tr>
          <td>LoRA</td>
          <td>BF16</td>
          <td>~150 GB</td>
          <td>多卡 A100 / H100</td>
      </tr>
      <tr>
          <td><strong>QLoRA</strong></td>
          <td>4-bit (NF4)</td>
          <td><strong>~40 GB</strong></td>
          <td>單張 A100 80GB / 雙 24GB GPU</td>
      </tr>
      <tr>
          <td>QLoRA on 7B</td>
          <td>4-bit</td>
          <td>~6-8 GB</td>
          <td>消費級 16GB+ GPU</td>
      </tr>
      <tr>
          <td>QLoRA on 30-32B</td>
          <td>4-bit</td>
          <td>~20-24 GB</td>
          <td>消費級 24GB+ GPU（5090）</td>
      </tr>
  </tbody>
</table>
<p>QLoRA 的核心創新（簡化）：</p>
<ol>
<li><strong>4-bit NormalFloat（NF4）量化</strong>：base model 用 4-bit 表示、精度損失低於原 INT4</li>
<li><strong>Double quantization</strong>：量化常數本身也量化、再省一點記憶體</li>
<li><strong>Paged optimizer</strong>：optimizer state 跑 CPU offload、避免訓練 spike OOM</li>
<li><strong>LoRA on 4-bit base</strong>：<a href="/blog/llm/knowledge-cards/lora/" data-link-title="LoRA" data-link-desc="Low-Rank Adaptation：凍住原模型權重、只訓兩個小矩陣的 parameter-efficient fine-tuning">LoRA</a> 訓的 A、B 矩陣仍是 BF16、只有 base 是 4-bit、推論時 dequantize → 加 LoRA → forward</li>
</ol>
<h2 id="設計責任">設計責任</h2>
<p>讀 fine-tuning 教學 / Hugging Face PEFT 文件看到「QLoRA」「bnb-4bit」就是這方法。寫 code 場景的判讀：</p>
<ol>
<li><strong>想 fine-tune 大模型在消費級硬體</strong>：QLoRA 是 default 選擇（不用 QLoRA、就只能訓 &lt; 7B）</li>
<li><strong>記憶體預算估算</strong>：QLoRA 訓 N B 模型約需 <code>0.6 × N GB</code> VRAM（30B → ~18GB、70B → ~42GB）</li>
<li><strong>品質 vs full fine-tune 差距</strong>：QLoRA 後合併權重的模型、實測跟 full fine-tune 接近（差距 &lt; 2-3%）、對多數場景可接受</li>
<li><strong>跟 <a href="/blog/llm/knowledge-cards/lora/" data-link-title="LoRA" data-link-desc="Low-Rank Adaptation：凍住原模型權重、只訓兩個小矩陣的 parameter-efficient fine-tuning">LoRA</a> 卡片區分</strong>：純 LoRA 是「base 不量化、訓 LoRA」、QLoRA 是「base 量化 4-bit、訓 LoRA」；QLoRA 是 LoRA 的延伸、不是替代</li>
<li><strong>推論時的選擇</strong>：QLoRA fine-tuned 模型可以「base 仍 4-bit + 載入 LoRA adapter」推論、記憶體用量低；也可以 merge 後用 GGUF Q4_K_M、跟 base 原相同</li>
</ol>
]]></content:encoded></item><item><title>5.2 KV cache 量化策略</title><link>https://tarrragon.github.io/blog/llm/05-discrete-gpu/kv-cache-quantization-strategy/</link><pubDate>Tue, 12 May 2026 00:00:00 +0000</pubDate><guid>https://tarrragon.github.io/blog/llm/05-discrete-gpu/kv-cache-quantization-strategy/</guid><description>&lt;p>KV cache 量化是 PC 場景開大 context 或提高併發數的常用工程選項：把 &lt;a href="https://tarrragon.github.io/blog/llm/knowledge-cards/kv-cache/" data-link-title="KV Cache" data-link-desc="已處理 token 的 attention 中間結果暫存：避免重算、加速後續生成">KV cache&lt;/a> 從 fp16 壓到 Q8 或 Q4、體積大幅縮減、騰出的 VRAM 拿去開長 &lt;a href="https://tarrragon.github.io/blog/llm/knowledge-cards/context-window/" data-link-title="Context Window" data-link-desc="模型一次能處理的最大 token 數量：prompt 加生成的總和上限">context&lt;/a>、加併發、或載入更大模型。本章不重複&lt;a href="https://tarrragon.github.io/blog/llm/knowledge-cards/kv-cache/" data-link-title="KV Cache" data-link-desc="已處理 token 的 attention 中間結果暫存：避免重算、加速後續生成">卡片定義&lt;/a>、改處理「實際要不要量化、量化到哪一級」的判讀。卡片視角的 &lt;a href="https://tarrragon.github.io/blog/llm/knowledge-cards/quantization/" data-link-title="Quantization" data-link-desc="用較少 bits 表示模型權重：壓縮記憶體佔用、加快生字速度，代價是少量品質衰減">量化&lt;/a> 跟本章的 KV cache 量化是兩個方向：前者壓模型權重、後者壓推論時的 attention 暫存。&lt;/p>
&lt;p>讀完本章後、你應該能對自己的工作流回答：KV cache 量化的好處能換到什麼、品質代價落在什麼範圍、K 跟 V 為什麼建議不同等級、跟 context 長度跟併發數怎麼搭配。&lt;/p>
&lt;h2 id="本章目標">本章目標&lt;/h2>
&lt;ol>
&lt;li>理解 KV cache 為什麼會隨 context 線性膨脹、為什麼 PC 場景常需要量化。&lt;/li>
&lt;li>區分 K 跟 V 在 attention 計算中的角色、解釋為何兩者對量化的容忍度不同。&lt;/li>
&lt;li>判讀「該不該量化 KV cache」的工作流類型。&lt;/li>
&lt;li>認識 llama.cpp 的 &lt;code>--cache-type-k&lt;/code> / &lt;code>--cache-type-v&lt;/code> 旗標與相關限制（如 flash attention 要求）。&lt;/li>
&lt;li>知道調參時的觀察訊號跟取捨方向。&lt;/li>
&lt;/ol>
&lt;h2 id="kv-cache-為什麼會膨脹">KV cache 為什麼會膨脹&lt;/h2>
&lt;p>LLM 推論時、每處理一個 token 都會把該 token 的 key 跟 value 向量算出來、暫存進 KV cache、供後續 token 的 attention 計算複用（不重算）。KV cache 的體積跟下面幾個變數線性相關：&lt;/p>





&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-text" data-lang="text">&lt;span class="line">&lt;span class="ln">1&lt;/span>&lt;span class="cl">KV cache 體積 ≈ 2 × n_layers × n_heads × head_dim × bytes_per_value × context_長度 × batch&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;ul>
&lt;li>2：分別是 K cache 跟 V cache&lt;/li>
&lt;li>n_layers / n_heads / head_dim：模型結構參數&lt;/li>
&lt;li>bytes_per_value：fp16 是 2 bytes、Q8_0 約 1 byte、Q4_0 約 0.5 byte&lt;/li>
&lt;li>context_長度：context 開多大、KV cache 就放多大&lt;/li>
&lt;li>batch：併發處理多少 sequence&lt;/li>
&lt;/ul>
&lt;p>實際 KV cache 體積依模型 attention 變體（MHA / GQA / MLA）、head 數設計、量化方式而變。比起背公式、更實用的做法是看 llama.cpp 啟動時的 log、它會列出實際 KV cache 配置的記憶體：&lt;/p>





&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-text" data-lang="text">&lt;span class="line">&lt;span class="ln">1&lt;/span>&lt;span class="cl">llm_load_print_meta: n_layer = 48
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="ln">2&lt;/span>&lt;span class="cl">llm_load_print_meta: n_head = 32
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="ln">3&lt;/span>&lt;span class="cl">llama_kv_cache_init: KV self size = 2048.00 MiB, K (q8_0): 1024.00 MiB, V (q8_0): 1024.00 MiB&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;blockquote>
&lt;p>&lt;strong>事實查核註&lt;/strong>：上面的 log 格式跟欄位名稱依 llama.cpp 版本變動、實際輸出以執行時為準。常見模型的 KV cache 估算工具可參考 &lt;a href="https://github.com/ggml-org/llama.cpp">llama.cpp 官方文件&lt;/a> 或社群維護的 calculator。&lt;/p></description><content:encoded><![CDATA[<p>KV cache 量化是 PC 場景開大 context 或提高併發數的常用工程選項：把 <a href="/blog/llm/knowledge-cards/kv-cache/" data-link-title="KV Cache" data-link-desc="已處理 token 的 attention 中間結果暫存：避免重算、加速後續生成">KV cache</a> 從 fp16 壓到 Q8 或 Q4、體積大幅縮減、騰出的 VRAM 拿去開長 <a href="/blog/llm/knowledge-cards/context-window/" data-link-title="Context Window" data-link-desc="模型一次能處理的最大 token 數量：prompt 加生成的總和上限">context</a>、加併發、或載入更大模型。本章不重複<a href="/blog/llm/knowledge-cards/kv-cache/" data-link-title="KV Cache" data-link-desc="已處理 token 的 attention 中間結果暫存：避免重算、加速後續生成">卡片定義</a>、改處理「實際要不要量化、量化到哪一級」的判讀。卡片視角的 <a href="/blog/llm/knowledge-cards/quantization/" data-link-title="Quantization" data-link-desc="用較少 bits 表示模型權重：壓縮記憶體佔用、加快生字速度，代價是少量品質衰減">量化</a> 跟本章的 KV cache 量化是兩個方向：前者壓模型權重、後者壓推論時的 attention 暫存。</p>
<p>讀完本章後、你應該能對自己的工作流回答：KV cache 量化的好處能換到什麼、品質代價落在什麼範圍、K 跟 V 為什麼建議不同等級、跟 context 長度跟併發數怎麼搭配。</p>
<h2 id="本章目標">本章目標</h2>
<ol>
<li>理解 KV cache 為什麼會隨 context 線性膨脹、為什麼 PC 場景常需要量化。</li>
<li>區分 K 跟 V 在 attention 計算中的角色、解釋為何兩者對量化的容忍度不同。</li>
<li>判讀「該不該量化 KV cache」的工作流類型。</li>
<li>認識 llama.cpp 的 <code>--cache-type-k</code> / <code>--cache-type-v</code> 旗標與相關限制（如 flash attention 要求）。</li>
<li>知道調參時的觀察訊號跟取捨方向。</li>
</ol>
<h2 id="kv-cache-為什麼會膨脹">KV cache 為什麼會膨脹</h2>
<p>LLM 推論時、每處理一個 token 都會把該 token 的 key 跟 value 向量算出來、暫存進 KV cache、供後續 token 的 attention 計算複用（不重算）。KV cache 的體積跟下面幾個變數線性相關：</p>





<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-text" data-lang="text"><span class="line"><span class="ln">1</span><span class="cl">KV cache 體積 ≈ 2 × n_layers × n_heads × head_dim × bytes_per_value × context_長度 × batch</span></span></code></pre></div><ul>
<li>2：分別是 K cache 跟 V cache</li>
<li>n_layers / n_heads / head_dim：模型結構參數</li>
<li>bytes_per_value：fp16 是 2 bytes、Q8_0 約 1 byte、Q4_0 約 0.5 byte</li>
<li>context_長度：context 開多大、KV cache 就放多大</li>
<li>batch：併發處理多少 sequence</li>
</ul>
<p>實際 KV cache 體積依模型 attention 變體（MHA / GQA / MLA）、head 數設計、量化方式而變。比起背公式、更實用的做法是看 llama.cpp 啟動時的 log、它會列出實際 KV cache 配置的記憶體：</p>





<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-text" data-lang="text"><span class="line"><span class="ln">1</span><span class="cl">llm_load_print_meta: n_layer    = 48
</span></span><span class="line"><span class="ln">2</span><span class="cl">llm_load_print_meta: n_head     = 32
</span></span><span class="line"><span class="ln">3</span><span class="cl">llama_kv_cache_init: KV self size = 2048.00 MiB, K (q8_0): 1024.00 MiB, V (q8_0): 1024.00 MiB</span></span></code></pre></div><blockquote>
<p><strong>事實查核註</strong>：上面的 log 格式跟欄位名稱依 llama.cpp 版本變動、實際輸出以執行時為準。常見模型的 KV cache 估算工具可參考 <a href="https://github.com/ggml-org/llama.cpp">llama.cpp 官方文件</a> 或社群維護的 calculator。</p></blockquote>
<h2 id="k-跟-v-為什麼適合用不同量化等級">K 跟 V 為什麼適合用不同量化等級</h2>
<p>K 跟 V 在 <a href="/blog/llm/knowledge-cards/attention/" data-link-title="Attention" data-link-desc="Transformer 內部讓每個 token 對其他 token 加權平均的核心機制、形成 KV cache 跟 context window 的計算基礎">attention</a> 計算中扮演不同角色、對量化的容忍度也不同。K 參與內積比較（量化容忍度通常較高）、V 是被加權平均的輸出內容（量化誤差會線性累積）、社群常見做法是 K 用較激進的量化、V 保留較高精度。</p>
<p>attention 的計算流程簡化為：</p>





<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-text" data-lang="text"><span class="line"><span class="ln">1</span><span class="cl">attention(Q, K, V) = softmax(Q · K^T / √d) · V</span></span></code></pre></div><p>K 跟 V 在這個流程中的角色差異：</p>
<ol>
<li><strong>K（key）</strong>：用來跟 Q 算內積、產生 attention score。內積本質是「相對量級的比較」、量化造成的微小誤差容易在 softmax 後被吸收。</li>
<li><strong>V（value）</strong>：是被 softmax 加權平均後直接輸出的內容、量化誤差會線性累積進輸出。</li>
</ol>
<p>社群多數回報指出：</p>
<ul>
<li><strong>K 用 Q8_0 或 Q4_0 對品質影響相對小</strong>：因為 softmax 對輸入量級的敏感度集中在最大值附近、其他位置的小幅誤差會被指數壓縮。</li>
<li><strong>V 用 Q4_0 在長 context 末尾較易出現品質下降</strong>：因為 V 是被加權平均的內容、累積誤差會在輸出中可見。</li>
</ul>
<blockquote>
<p><strong>事實查核註</strong>：K 跟 V 對量化敏感度不同的論述、來自社群常見回報跟若干針對 KV cache 量化的論文（如 KIVI、KVQuant 等）。具體影響因模型架構、量化方法（symmetric / asymmetric、per-head / per-channel scale 等）變化、不同模型的表現可能不一致；建議用自己工作流的任務跟自己選定的量化版本實測校準。</p></blockquote>
<h2 id="kv-cache-量化等級對照">KV cache 量化等級對照</h2>
<p>llama.cpp 支援的常見 KV cache 量化等級：</p>
<table>
  <thead>
      <tr>
          <th>量化等級</th>
          <th>bytes/value（約）</th>
          <th>相對 fp16 體積</th>
          <th>社群常見用途</th>
      </tr>
  </thead>
  <tbody>
      <tr>
          <td><code>fp16</code></td>
          <td>2</td>
          <td>100%</td>
          <td>預設、品質基準</td>
      </tr>
      <tr>
          <td><code>q8_0</code></td>
          <td>1</td>
          <td>50%</td>
          <td>K 的常見起點、品質衰減社群回報為小幅</td>
      </tr>
      <tr>
          <td><code>q5_1</code></td>
          <td>~0.7</td>
          <td>~35%</td>
          <td>中間選項</td>
      </tr>
      <tr>
          <td><code>q5_0</code></td>
          <td>~0.7</td>
          <td>~35%</td>
          <td>中間選項</td>
      </tr>
      <tr>
          <td><code>q4_1</code></td>
          <td>~0.5</td>
          <td>~25%</td>
          <td>V 的常見極限</td>
      </tr>
      <tr>
          <td><code>q4_0</code></td>
          <td>~0.5</td>
          <td>~25%</td>
          <td>V 的常見起點、品質衰減較 Q5 略大</td>
      </tr>
  </tbody>
</table>
<p>常見組合（社群回報、需自行校準）：</p>
<ul>
<li><strong>保守（品質優先）</strong>：K=fp16、V=fp16。完全不量化、VRAM 用量最大。</li>
<li><strong>平衡起點</strong>：K=Q8_0、V=Q8_0。體積約一半、品質衰減社群多數回報為小幅或不明顯。</li>
<li><strong>激進（context 優先）</strong>：K=Q8_0、V=Q4_0。體積約 fp16 的 35%、社群回報短 prompt 影響小、長 prompt 末尾可能出現品質下降。</li>
<li><strong>極限</strong>：K=Q4_0、V=Q4_0。體積約 fp16 的 25%、用於開超大 context 或極高併發、品質風險最高。</li>
</ul>
<h2 id="何時值得量化何時不該量化">何時值得量化、何時不該量化</h2>
<p>KV cache 量化的主要用途是「VRAM 不足以同時放下模型權重 + 目標 context 長度 + 目標併發數」的場景。當 VRAM 已有充裕餘量、量化省下的 VRAM 沒有對應的用途時、保留 fp16 通常較合適。下表整理常見的判讀情境：</p>
<table>
  <thead>
      <tr>
          <th>場景</th>
          <th>是否值得量化</th>
          <th>主要考量</th>
      </tr>
  </thead>
  <tbody>
      <tr>
          <td>寫 code、補完、跨檔案重構</td>
          <td>值得（K=Q8/V=Q4）</td>
          <td>程式碼合法性約束會過濾小幅誤差、社群回報品質影響小</td>
      </tr>
      <tr>
          <td>RAG（大型 codebase 索引、長文件摘要）</td>
          <td>值得</td>
          <td>context 通常很長、KV cache 是 VRAM 主要瓶頸</td>
      </tr>
      <tr>
          <td>自由創作（小說、長對話、詩）</td>
          <td>評估、可能不適合</td>
          <td>V 量化的累積誤差較易在創作品質上感知</td>
      </tr>
      <tr>
          <td>數學 / 邏輯推理（chain-of-thought）</td>
          <td>從保守起點</td>
          <td>推理鏈累積誤差較敏感、建議從 K=Q8 / V=Q8 起步、再依任務評估</td>
      </tr>
      <tr>
          <td>短 prompt 短回答（&lt; 4K context）</td>
          <td>不必要</td>
          <td>KV cache 體積本來就小、量化省下的 VRAM 不多</td>
      </tr>
      <tr>
          <td>對品質高度敏感的研究或產品任務</td>
          <td>從保守起點</td>
          <td>先用 fp16 建立品質基準、再依需求逐步量化、確認品質可接受</td>
      </tr>
  </tbody>
</table>
<p>判讀原則：<strong>先確認瓶頸是「VRAM 不夠」還是「品質不夠」</strong>。前者量化是解法、後者量化通常會惡化問題。</p>
<h2 id="跟-context-長度併發數的協調">跟 context 長度、併發數的協調</h2>
<p>KV cache 量化的好處要跟其他 VRAM 用量一起評估。常見的取捨方向：</p>
<ol>
<li><strong>量化 → 開更大 context</strong>：把省下的 VRAM 用在加大 <code>-c</code>、能開長 prompt（如 RAG、長對話、跨檔案分析）。</li>
<li><strong>量化 → 加併發</strong>：把省下的 VRAM 用在加 <code>--parallel</code>、能同時服務多個 client（如多個編輯器視窗、多 agent）。</li>
<li><strong>量化 → 載入更大模型</strong>：把省下的 VRAM 用在降 <code>--n-cpu-moe</code>、減少卸載、提升生字速度。</li>
</ol>
<p>三者通常不能同時極大化、需要依工作流挑主軸。</p>
<p>實務上的常見搭配（社群回報、需校準）：</p>
<table>
  <thead>
      <tr>
          <th>工作流</th>
          <th>建議搭配</th>
      </tr>
  </thead>
  <tbody>
      <tr>
          <td>單人寫 code、補完為主</td>
          <td>K=Q8 / V=Q4、context 32K ~ 128K、<code>--parallel 1 ~ 2</code></td>
      </tr>
      <tr>
          <td>RAG 大型 codebase</td>
          <td>K=Q8 / V=Q4、context 128K ~ 256K、<code>--parallel 1</code></td>
      </tr>
      <tr>
          <td>多 agent / 多視窗並用</td>
          <td>K=Q8 / V=Q4 或更激進、context 32K、<code>--parallel 4 ~ 8</code></td>
      </tr>
      <tr>
          <td>對話品質敏感、純創作</td>
          <td>K=Q8 / V=Q8 起步、context 適中、依品質確認再決定是否加量化</td>
      </tr>
  </tbody>
</table>
<h2 id="llamacpp-的相關旗標">llama.cpp 的相關旗標</h2>
<p>跑 KV cache 量化時、常用的旗標：</p>
<table>
  <thead>
      <tr>
          <th>旗標</th>
          <th>作用</th>
          <th>備註</th>
      </tr>
  </thead>
  <tbody>
      <tr>
          <td><code>--cache-type-k &lt;type&gt;</code></td>
          <td>K cache 量化（如 <code>f16</code>、<code>q8_0</code>、<code>q4_0</code>）</td>
          <td>預設 f16</td>
      </tr>
      <tr>
          <td><code>--cache-type-v &lt;type&gt;</code></td>
          <td>V cache 量化</td>
          <td>預設 f16</td>
      </tr>
      <tr>
          <td><code>-fa</code> / <code>--flash-attn</code></td>
          <td>啟用 flash attention</td>
          <td>部分量化組合需要 flash attention 才能啟用、見下方說明</td>
      </tr>
      <tr>
          <td><code>-c &lt;N&gt;</code></td>
          <td>context window 大小</td>
          <td>KV cache 體積跟此線性相關</td>
      </tr>
      <tr>
          <td><code>--parallel &lt;N&gt;</code></td>
          <td>併發處理數</td>
          <td>KV cache 體積跟此線性相關</td>
      </tr>
      <tr>
          <td><code>-ctk &lt;type&gt;</code> / <code>-ctv &lt;type&gt;</code></td>
          <td><code>--cache-type-k</code> / <code>--cache-type-v</code> 的短旗標</td>
          <td>同義、版本依 llama.cpp 變動</td>
      </tr>
  </tbody>
</table>
<h3 id="flash-attention-的關係">flash attention 的關係</h3>
<p>部分 KV cache 量化組合（特別是 V=Q4_0 / Q4_1）在 llama.cpp 上需要同時啟用 <a href="/blog/llm/knowledge-cards/flash-attention/" data-link-title="Flash Attention" data-link-desc="Attention 計算的記憶體友善實作、減少 GPU memory 讀寫、提升長 context 推論吞吐">flash attention</a>（<code>-fa</code>）才能正常運作；沒啟用時可能載入失敗或 fallback 到 fp16。具體要求依 llama.cpp 版本變化、以實際 <code>llama-server --help</code> 跟 <a href="https://github.com/ggml-org/llama.cpp/pulls?q=is%3Amerged&#43;kv&#43;cache&#43;quant">llama.cpp 官方 issue / PR</a> 為準。</p>
<blockquote>
<p><strong>事實查核註</strong>：flash attention 對 KV cache 量化組合的限制、是 llama.cpp 實作層面的演進議題、不是模型本身的限制。新版 llama.cpp 可能放寬或改變要求、引用前以最新版的 release notes 為準。</p></blockquote>
<h2 id="給讀者的調參步驟">給讀者的調參步驟</h2>
<p>實際設定 KV cache 量化時、可以照下面的步驟調：</p>
<ol>
<li><strong>先用 fp16 基準跑一次</strong>：用實際工作流的代表性任務、記錄補完品質、執行時間、VRAM 用量。這是後續比較的基準。</li>
<li><strong>切到 K=Q8 / V=Q8</strong>：跑同樣的任務、比較品質。社群多數回報差異不明顯、但需以自己工作流確認。</li>
<li><strong>進一步切到 V=Q4</strong>：再跑同樣任務、特別注意長 prompt 末尾、推理鏈、複雜邏輯任務的輸出品質。</li>
<li><strong>若品質可接受、評估省下的 VRAM 怎麼用</strong>：加大 <code>-c</code>、提高 <code>--parallel</code>、或減少 <code>--n-cpu-moe</code>。</li>
<li><strong>建立可重複的校準腳本</strong>：把代表性任務寫成 prompt 集、做為日後升級模型或調參時的回歸測試。</li>
</ol>
<h2 id="下一章">下一章</h2>
<p>下一章：<a href="/blog/llm/05-discrete-gpu/llama-cpp-on-pc/" data-link-title="5.3 llama.cpp 在 PC 上" data-link-desc="CUDA / ROCm build 取得、核心旗標地圖、llama-bench 校準、多卡 tensor split 的入門設定">5.3 llama.cpp 在 PC 上</a>、把本章跟 <a href="/blog/llm/05-discrete-gpu/moe-cpu-offload-strategy/" data-link-title="5.1 MoE 模型與 CPU 卸載策略" data-link-desc="PC 場景把 MoE 不活躍專家層留在系統 RAM 的判讀：何時值得卸載、卸幾層、對 prefill 跟生成的影響各自不同">5.1 MoE 卸載</a> 的旗標放進完整的 llama.cpp 調參工作流。</p>
]]></content:encoded></item></channel></rss>