Skip to content

Speculative Decoding

Draft a block, verify its prefix

Keep the accepted prefix and select one more token

Thecatsatonthe

Output: 3 accepted drafts + 1 residual replacement = 4 tokens.

The cat sat beside

Scripted word-sized chunks, not a tokenizer or distribution-correct sampler. Tokens after the first rejection are discarded; the bonus appears only when all drafts are accepted.

Ordinary autoregressive decoding is sequential, and small-batch decode is often memory-bound. Each new token requires a full forward pass through the model, reading every weight from memory, and most of the GPU's compute sits idle while that happens. We established this in Prefill vs. Decode and The One New Row.

Faster kernels, lower precision, and different hardware can reduce a decode step's cost. Speculation asks a different question: can one target pass advance several output positions?

Speculative decoding uses an accept/reject rule that preserves the target model's sampling distribution.


Prerequisites

Prefill vs. Decode (Post 5.2) explains the prefill/decode asymmetry, and The One New Row (Post 5.3) derives the weight traffic per decode step. The acceptance rule below compares probability distributions over the token vocabulary.


The core asymmetry

As in Post 5.2, prefill processes prompt positions in parallel. You hand the model 1,000 tokens and it processes all 1,000 in one forward pass, computing attention across all positions simultaneously. Processing 1,000 tokens performs far more arithmetic than processing one. The useful window for speculation is a small candidate block that can use otherwise idle compute without greatly increasing target-pass latency.

Verification can reuse that parallelism. If someone hands you kk candidate tokens and says "what would you have predicted at each of these positions?", the target model can answer that question for all kk positions in a single forward pass, at roughly the cost of processing a prompt of length kk.

Ordinary autoregressive generation cannot do this: each sampled token becomes input for the next prediction. Verification already has the candidate sequence available.

When additional verification work fits below a memory bound

Hypothetical hardware with enough memory: reading weights takes at least 70 ms; compute takes at least 0.45 ms per position. These are independent bounds, not two serial phases.

Weight-read bound70.00 ms
Compute bound2.25 ms

Combined lower bound: max(70, 2.25) = 70.00 ms.

Real verification also reads KV state and incurs kernel and scheduling costs. Drafting costs extra. Verification is not free, and a large enough block becomes compute-bound.

Increase the candidate block to compare independent memory and compute lower bounds. Small blocks can reuse a weight read, but verification and drafting still cost time.

Draft, then verify

The draft-and-verify setup uses two models:

  1. A draft model that's small and fast. Something like a 1B parameter distilled version of your target, or even a separate lightweight model.
  2. A target model that's the big one you actually want output from. Think 70B parameters.

The draft model generates kk candidate tokens autoregressively, each conditioned on the previous tokens. An illustrative pairing is Llama-2-7B drafting for Llama-2-70B, or a purpose-built 1B distilled model drafting for a 70B+ target. The draft must be fast enough that its extra work costs less than the target steps it saves.

The target evaluates the candidate block with causal attention. Logits at a position predict the next token: the first candidate is checked against the distribution after the accepted prefix, not against the logits produced after consuming that candidate. Implementations retain that prefix prediction or include its last unprocessed token in the verification call. The aligned predictions check all kk candidates and provide the next-position distribution for a bonus token.

Toy rounds: fixed 80% conditional acceptance
DRAFT MODELsmall, fastTARGET MODELtarget distributionClick "Run round" to watch one round of speculative decoding

A structural toy with fixed 80% conditional acceptance and illustrative replacement words. It shows accepted prefixes and discarded suffixes; it does not implement the distribution-correct sampler derived below.

Verification has a cost; for a small candidate block it can be close to a single decode pass in a bandwidth-limited regime. You're already loading all the weights for a decode step anyway, so you might as well use them on kk tokens instead of 1. The batch-one, weights-only FP16 example in Post 5.3 has roughly 1 FLOP per byte. Processing kk tokens during verification bumps the arithmetic intensity to kk FLOPs per byte, still well within the memory-bound regime, so the additional target cost can be modest. Cache traffic, batch size, candidate count, and kernel overhead determine the actual result.


The acceptance criterion

So the target model processes all kk draft tokens in one forward pass and produces logits at every position. At each position ii, you now have two probability distributions:

  • q(xi)q(x_i): the probability the draft model assigned to the token it chose
  • p(xi)p(x_i): the probability the target model assigns to that same token

The rule works left to right, position by position:

If p(xi)≥q(xi)p(x_i) \geq q(x_i): accept. The target assigns this token at least as much probability as the draft does.

If p(xi)<q(xi)p(x_i) < q(x_i): accept with probability p(xi)q(xi)\frac{p(x_i)}{q(x_i)}, reject otherwise. If you reject, you don't just throw the token away. You resample from an adjusted distribution:

p′(x)=norm(max⁡(0,  p(x)−q(x)))p'(x) = \text{norm}\big(\max(0,\; p(x) - q(x))\big)

This adjusted distribution captures the probability mass that the target model wants to assign but the draft model didn't. You sample one token from p′p', use it as the replacement, and discard everything after the rejection point.

Acceptance and the residual distribution

Acceptance probability α = Σ min(p, q) = 93.0%.

TokenpqAcceptResidual
sat0.350.30100%71.4%
stood0.250.2889%0.0%
lay0.150.1883%0.0%
slept0.120.10100%28.6%
fell0.080.0989%0.0%
rested0.050.05100%0.0%

The residual column is max(p−q, 0), normalized across the vocabulary. Draw from it only after rejection. Acceptance is conditional on proposing the token in that row.

Full bar = 100% of proposal mass. Indigo is accepted; the remainder is replaced by a residual sample.

Toggle between draft quality levels to see how the acceptance criterion changes. When p >= q, a token is accepted outright. When p < q, the coin flip probability p/q gets worse. The residual column shows where resampled tokens come from.

And then you start a new round. The draft model picks up from the last accepted (or resampled) token and guesses another kk tokens. After a rejection, discard the suffix from the draft and target caches as well as from the output. This cycle repeats until an accepted or sampled end-of-sequence token, or another stopping condition.


The correctness guarantee

Leviathan et al. and Chen et al. both independently proved that this accept/reject scheme produces the same sampling distribution as the target model in exact arithmetic, using the normalized draft and target distributions after their sampling transformations.

This is rejection sampling: the draft distribution qq is the proposal, and the acceptance rule corrects its mismatch with the target pp. A poor proposal increases rejection without changing the resulting distribution.

For a token xx, the accepted probability mass is q(x)min⁡(1,p(x)/q(x))=min⁡(p(x),q(x))q(x)\min(1,p(x)/q(x))=\min(p(x),q(x)). Write α=∑xmin⁡(p(x),q(x))\alpha=\sum_x\min(p(x),q(x)). Rejection occurs with probability 1−α1-\alpha, and the residual distribution normalizes max⁡(p−q,0)\max(p-q,0) by that same quantity. Thus the total output mass is

min⁡(p(x),q(x))+max⁡(p(x)−q(x),0)=p(x).\min(p(x),q(x)) + \max(p(x)-q(x),0) = p(x).

Resampling directly from pp would instead give min⁡(p(x),q(x))+(1−α)p(x)\min(p(x),q(x))+(1-\alpha)p(x), which generally differs from p(x)p(x). When α=1\alpha=1, rejection never occurs and no residual distribution is needed.

Equal distributions do not imply the same token sequence for an arbitrary random seed. Finite-precision implementations can also introduce rounding differences.


How much faster?

The speedup depends on the acceptance rate α\alpha, the probability that any given draft token gets accepted. If the draft model closely matches the target model's distribution, α\alpha is high and most candidates are accepted.

Under the simplifying assumption of a constant conditional acceptance probability α\alpha at each candidate position, the expected token yield per target pass is:

tokens per step=1−αk+11−α\text{tokens per step} = \frac{1 - \alpha^{k+1}}{1 - \alpha}

where kk is the number of draft tokens per round. At α=1\alpha=1, use the limit k+1k+1 (or the equivalent sum 1+α+⋯+αk1+\alpha+\cdots+\alpha^k). Some examples:

  • α=0.8\alpha = 0.8, k=4k = 4: about 3.4 tokens per step. That is token yield per target pass, not wall-clock speedup.
  • α=0.9\alpha = 0.9, k=5k = 5: about 4.7 tokens per step.
  • α=0.5\alpha = 0.5, k=4k = 4: about 1.9 tokens per step.
Expected Tokens Per Step vs. Acceptance Rate
α = 0.80
Assume the same conditional acceptance probability α at every position. Draft and verification latency are excluded.
k=3: 2.95 outputs/passk=5: 3.69 outputs/passk=7: 4.16 outputs/passk=10: 4.57 outputs/pass
12468100.00.20.40.60.81.0acceptance rate (α)tokens / step1
α = 0α = 1.00

Drag the slider to see how the expected tokens per step changes with acceptance rate. Higher k means more draft tokens per round, which pays off when the acceptance rate is high. Below alpha ~0.5, adding more draft tokens barely helps.

The k+1k+1 in the exponent accounts for the bonus token. Even when a draft token is rejected, you resample one new token from the target model's adjusted distribution. If all kk drafts are accepted, sample the bonus token from the target distribution at the next position. An immediate rejection yields one replacement token, but still incurs the wasted draft work.

For wall-clock speedup, divide expected token yield by the round cost relative to an ordinary target step. If cc is draft cost per token and vkv_k is verification cost, both in target-step units, the estimate is E[N]/(kc+vk)E[N]/(kc+v_k). Low acceptance or expensive drafting can make this less than one.

Leviathan et al. reported 2–3× acceleration for their T5-XXL experiments.


A worked example

The following round uses constructed probabilities and a chosen coin-flip outcome.

Say we're mid-generation. The context so far is the beginning of a new sentence and the draft model proposes five tokens: "The", "cat", "sat", "on", "the".

The target model processes all five in one forward pass and produces its own probability distribution at each position. Going left to right:

  1. "The" — target gives it p=0.85p = 0.85, draft had q=0.70q = 0.70. Since p≥qp \geq q, accept.
  2. "cat" — target gives p=0.40p = 0.40, draft had q=0.35q = 0.35. Since p≥qp \geq q, accept.
  3. "sat" — target gives p=0.30p = 0.30, draft had q=0.25q = 0.25. Since p≥qp \geq q, accept.
  4. "on" — target gives p=0.10p = 0.10, draft had q=0.30q = 0.30. Since p<qp < q, we flip a coin with probability p/q=0.33p/q = 0.33. The coin comes up reject. We resample from norm(max⁡(0,p−q))\text{norm}(\max(0, p - q)) across the full vocabulary and get "down".
  5. "the" — discarded. Everything after the rejection point gets thrown away.

Net result: 3 accepted tokens + 1 resampled token = 4 tokens from one target forward pass. The generation continues from "down", and the draft model starts a new round from there.

Toy probabilities — position by position
p (target)q (draft)pos 1The0.850.70accept (p>=q)Thepos 2cat0.400.35accept (p>=q)catpos 3sat0.300.25accept (p>=q)satpos 4on0.100.30coin rejecteddownresampledpos 5theafter rejectionOUTPUTpos 5: discarded, everything after the rejection is thrown away
Accepted: 3
Resampled: 1
Total from one target pass: 4

Step to position 4 and compare the rejected candidate, the replacement, and the discarded suffix.

For "on," the rejection probability was 1−p/q=0.671 - p/q = 0.67. The replacement comes from the residual distribution, not from the target’s top token or directly from pp. That correction accounts for the probability mass already supplied by accepted draft tokens.


When it works and when it doesn't

Acceptance is determined by overlap between the draft and target distributions: at one position, α=∑xmin⁡(p(x),q(x))\alpha=\sum_x\min(p(x),q(x)). Predictable continuations can help when both models concentrate on the same tokens, but low entropy alone does not ensure agreement. Measure acceptance on the actual prompts, sampling settings, and draft/target pair. A mismatched draft can remain poor even on syntactically constrained text.


Beyond draft models: Medusa

A separate draft model needs deployment and memory alongside the target. It must produce distributions over the same token vocabulary, run cheaply, and overlap enough with the target distribution to repay its cost.

Cai et al. proposed a different approach called Medusa. Instead of a separate draft model, you add extra prediction heads to the target model itself. Alongside the standard language-model head that predicts position t+1t+1, you train additional lightweight heads that predict positions t+2t+2, t+3t+3, t+4t+4, and so on.

Each Medusa head is a small feedforward network on the target model’s last hidden state. A subsequent pass verifies the proposed continuations.

The extra heads avoid deploying a separate draft model. Medusa-1 trains them while freezing the backbone; Medusa-2 also trains the backbone. Their training and acceptance costs differ.

Medusa also introduced tree-structured verification. Instead of proposing a single linear sequence of kk tokens, you generate a tree of candidates. At position t+2t+2, you might have three candidates (from the Medusa head's top-3 predictions). At t+3t+3, candidates from the next prediction head form further branches; the same head’s candidates can appear under multiple earlier choices. You verify the entire tree in one forward pass using carefully constructed attention masks. The best path through the tree gives you the longest accepted prefix. This can accept a longer path than a single chain because a single bad prediction at one position doesn't necessarily waste all subsequent positions.

Linear vs. Tree Verification (Medusa)

Gray descendants of a rejected branch are discarded. This selected candidate tree is schematic; it does not expand every combination of prediction-head candidates.

LINEAR DRAFTstandard spec decodeTREE (MEDUSA)multiple heads, branchingThecatranfasttodayThedogcatransatdownstill

A constructed example of linear and tree candidates. A rejected branch can leave another path available. The highlighted paths illustrate verification structure, not measured acceptance or a speedup guarantee.

The earlier work by Stern et al. explored a similar idea called blockwise parallel decoding. Medusa refined it with better training objectives and the tree attention mechanism.

Medusa’s extra heads predict future positions from a shared current hidden state. Their candidates do not acquire the same token-by-token conditioning as an autoregressive draft model.

Medusa’s typical acceptance policy can trade distribution fidelity for speed, so the exact rejection-sampling guarantee above does not automatically apply to every configuration.


Common misconceptions

"Speculative decoding is an approximation." The exact accept/reject algorithm preserves the target distribution in exact arithmetic. Use the actual post-temperature/filter proposal and target distributions in the acceptance calculation; heuristic acceptance variants need separate analysis.

"The draft model needs to be the same architecture." No. Any model works as long as it shares the tokenizer (or at least the token vocabulary). You could use a tiny 2-layer transformer as a draft for a giant 80-layer MoE model. The architecture is irrelevant because the acceptance criterion only compares probability distributions over tokens, not internal representations. What matters is that both models produce distributions over the same vocabulary.

"Speedup is always k×k\times." The maximum output yield is k+1k + 1 tokens per target pass when every draft is accepted. Wall-clock speedup also depends on verification time and draft cost. And you have to account for the overhead of running the draft model. If the draft model's full kk-step round (all 4 drafts together, not per draft) takes about 20% of the time of one target-model step, your effective speedup at α=0.8,k=4\alpha = 0.8, k = 4 is roughly 3.4/1.2≈2.8×3.4 / 1.2 \approx 2.8\times, not 3.4×3.4\times.

"It helps equally with throughput and latency." Speculative decoding primarily helps latency for individual requests. In high-throughput serving with large decode batches, the GPU utilization is already decent from batching, and the draft model competes for the same GPU resources. For throughput-optimized workloads with large batch sizes, the benefit is often minimal.

What's next

The small-batch weight traffic derived in Post 5.3 can also be amortized across independent requests.

The next post covers continuous batching, how inference engines schedule many requests at once by interleaving their prefill and decode steps, so queued work can enter at iteration boundaries.


Additional reading (and watching)