Exercises — KV-cache optimization
Before we start, one shared picture of the two worlds — "recompute everything" vs "remember and append":

Reading the figure. The top row is generation without a cache at step 4: all four key boxes are drawn in black because the model recomputes every one of them from scratch. The bottom row is generation with a cache: are black (already stored, just reused — follow the "reuse" arrow) and only is drawn in red, because it is the single new projection the cache must compute this step. That contrast — three reused vs one new — is the whole idea of the cache, and every memory/FLOP problem below is just counting these boxes.
Level 1 — Recognition
Exercise 1.1 (L1)
State which of the following are stored in the KV-cache during autoregressive generation, and which are recomputed every step: (a) key projections , (b) value projections , (c) query projections , (d) the final softmax attention weights.
Recall Solution
- (a) — cached. A past token's key never changes once computed, so we store it (the black boxes in Figure s01).
- (b) — cached, same reason.
- (c) — recomputed each step. The query is "what the current token is looking for," and there is a brand-new current token every step, so there is nothing to reuse (the red box is new every step).
- (d) softmax weights — recomputed. They depend on the new , so they change every step.
The cache stores exactly the things that are fixed for past positions: and . Hence the name KV-cache.
Exercise 1.2 (L1)
Recognition of shape. A single layer has heads and head dimension . After generating 5 tokens, what is the shape of (as tokens × heads × head-dim)?
Recall Solution
Each token contributes one key per head: shape per token is . Stacking 5 tokens gives has the identical shape. The first axis (here ) is the only one that grows as we generate.
Level 2 — Application
Exercise 2.1 (L2)
Per-token cache memory. A layer has heads, , stored in fp16 (2 bytes each). How many bytes does one token add to the KV-cache for that one layer?
Recall Solution
Where the formula comes from (short derivation). For one token we must store its keys and its values. A single token's key set is one -vector per head, so it has numbers; the same holds for the value set. That is two tensors of numbers, and each number occupies "precision" bytes. Multiply: That is the whole reason for each factor — nothing is cited blindly. Plug in: (Recall the unit convention: bytes exactly.)
Exercise 2.2 (L2)
Full-model cache for a whole sequence. Same layer specs (, , fp16), now and a sequence of tokens. Total cache size in gigabytes?
Recall Solution
One token in one layer costs the from Ex 2.1. We now have tokens (first cache axis grows) and independent layers (each keeps its own cache), so we multiply by both: Plug in: Step it: ; ; ; ; bytes. Convert (binary GB): GB. Answer: GB ( MB, since ).
Exercise 2.3 (L2)
Speedup factor. Recall is the model width, and each of projects a token's -vector into a -vector, costing multiply-adds per token. Without caching, at step the model re-projects all tokens, and summing over the whole generation makes the projection work scale as ; with caching it re-projects only the one new token per step, giving . First derive why the no-cache total is , then compute the projection speedup for .
Recall Solution
Why the no-cache cost is (the missing "why"). One token's three projections cost each — because multiplying a -vector by a matrix is multiply-adds — so per token. Without a cache, at generation step the model treats the sequence as fresh and re-projects all tokens seen so far, costing that step. Summing over every step : The quadratic in comes purely from the triangular sum . With a cache, only the one new token is projected per step: . Speedup: The cancels — the speedup is purely the sequence-length factor . Longer generations benefit more.
Level 3 — Analysis
Exercise 3.1 (L3)
MQA vs standard. A model uses query heads, . Compare the KV-cache size of standard multi-head attention against Multi-Query Attention (MQA), which shares a single K/V head. Give the ratio and interpret.
Recall Solution
Standard cache (per token, per layer, ignoring the constant factor): MQA keeps one K and one V head: Ratio: MQA uses less KV-cache. Interpretation: query heads still specialize (each has its own ), but they all read from the same keys and values, so we only store one set. Cost: a small quality drop (~1–2% perplexity).
Exercise 3.2 (L3)
GQA middle ground. Llama-2 70B uses query heads grouped into K/V groups. (a) What is the cache reduction versus standard attention? (b) Where does GQA sit between standard and MQA?

Reading the figure. Three head-sharing schemes are drawn side by side. The top boxes are the query heads; the bottom boxes are the stored KV heads; each line shows which queries read which KV. Left ("standard "): every query has its own private KV — no sharing, maximal cache. Right ("MQA "): all queries funnel into one shared KV — minimal cache. Middle ("GQA ", drawn in red): queries are bundled into groups, each group sharing one KV — the tunable middle ground. As you slide from down to , you slide the cache from "standard" down to "MQA"; the red middle is exactly the case part (b) asks about.
Recall Solution
(a) GQA stores K/V heads instead of : So 8× reduction. (b) Read the figure left-to-right: standard has one K/V head per query head (, no reduction); MQA collapses to a single shared K/V head (, maximal reduction); GQA (the red grouping in the middle) sits between with . It recovers most of MQA's memory savings while keeping more of standard attention's quality by giving each group of queries its own keys/values.
Exercise 3.3 (L3)
Sliding-window memory. For a 100K-token context, compare full-cache memory to a sliding-window cache of width . Assume , , , fp16. Give both sizes and the ratio.
Recall Solution
Per-token-per-layer bytes: B KB. Full cache (): (Binary conversion: GB.) Sliding-window (): Ratio: smaller. Trade-off: the window keeps memory constant at regardless of context length, but the model literally cannot attend to anything older than tokens — long-range dependencies past the window are lost.
Level 4 — Synthesis
Exercise 4.1 (L4)
FLOP accounting, cache vs no-cache. For GPT-2 small (, model width ), estimate projection FLOPs to generate tokens with and without caching. Report both and the speedup.
Recall Solution
Where the per-step cost comes from. As established in Ex 2.3, projecting one token through a matrix costs multiply-adds; we treat the three projections as and drop the small constant factor (the "3" and any terms) because we only want the scaling with and the ratio — constants cancel in the ratio anyway. So:
- No-cache, step , per layer: re-project all tokens .
- Cache, step , per layer: project only the 1 new token .
Without cache — sum the triangular series over all steps, times layers: (Used — the same triangular sum as Ex 2.3.) With cache — one new K/V/Q per step, so per step: Speedup: This matches the expected factor: the sum-of-integers gives vs , i.e. . The dropped constant factor never mattered because it appears identically in both numerator and denominator.
Exercise 4.2 (L4)
Design under a memory budget. You have a 24 GB GPU. Model weights take 14 GB, leaving 10 GB for KV-cache. Layer specs: , , , fp16. (a) What is the maximum context length you can cache with standard attention? (b) With GQA at ?
Recall Solution
Per-token, all-layers, standard: Budget GB B (binary GB). (a) tokens. (b) GQA with replaces the head count by in K/V → the per-token size KB/token: Design conclusion: switching to GQA() quadruples the affordable context length under the same memory budget.
Level 5 — Mastery
Exercise 5.1 (L5)
Crossover analysis. MQA saves memory but you worry about quality. Suppose standard attention gives perplexity and MQA gives (a increase). Meanwhile MQA lets you cache more tokens. If longer context reduces perplexity by roughly when context grows (empirical), does trading standard→MQA to buy context help or hurt perplexity net?
Recall Solution
Two effects compose multiplicatively on perplexity:
- MQA head-sharing penalty: factor (worse).
- longer usable context: factor (better). Net factor: Since , net perplexity drops by ~0.53% — the context gain outweighs the sharing penalty. Mastery point: memory optimizations are not "free lunch vs pure cost"; they enable longer context, which itself improves quality. You must weigh the direct penalty against the capability it unlocks.
Exercise 5.2 (L5)
Full stack estimate. Combine everything: , , , fp16, and you deploy GQA() with a sliding window for a nominal 200K-token context. (a) What would the full standard cache have cost at 200K tokens? (b) What does the GQA + sliding-window cache actually cost? (c) Combined reduction factor?
Recall Solution
Standard per-token-all-layers: (Binary: MB.) (a) Full standard at : (b) GQA cuts K/V heads , factor → per-token KB. Sliding window caps tokens at : (c) Reduction: Interpretation: two orthogonal levers multiply — GQA gives (head sharing) and the window gives (bounded length), and . This is why production long-context serving (7.2.1-llm-deployment, 6.2.3-inference-optimization) stacks multiple cache tricks rather than relying on one.
Recall Quick self-check summary
Cache holds K and V only ::: queries are fresh each step Memory formula leading constant ::: 2, for K and V Model width in terms of heads ::: Standard→MQA cache ratio ::: GQA() cache ratio ::: Projection speedup from caching ::: factor Sliding window memory order ::: , constant in Combining independent cache savings ::: multiply the factors
Related: 6.1.11-sparse-attention, 6.3.1-model-quantization, 5.4.2-beam-search, 6.1.13 KV-cache optimization (Hinglish).