Yesterday we looked at mechanistic interpretability: trying to understand the internal features and circuits that make a Transformer produce an answer.
Today we'll zoom in on the piece of the architecture that makes those circuits much easier to reason about:
The residual stream is a shared communication channel running through the entire Transformer.
Attention heads and MLPs don't usually pass private messages directly to one another. Instead, they repeatedly read from and write to this common vector.
A useful first approximation is:
Understanding this one idea makes the architecture feel much less like a mysterious stack of layers.
Start with the usual picture¶
We often draw a Transformer like this:
tokens
↓
embedding
↓
attention
↓
MLP
↓
attention
↓
MLP
↓
...
↓
logits
That picture suggests each component replaces the representation produced by the previous one.
But modern Transformers are built around residual connections.
A better picture is:
attention
↗ ↘
residual ───────────────────── residual
stream stream
↘ ↗
MLP
Each component computes some update and adds it to the existing state.
Schematically:
where:
- \(x_l\) is the current residual-stream state,
- \(f_l\) is an attention or MLP computation.
The old information is not discarded.
The component contributes a delta.
One token has one residual vector at each layer¶
Suppose:
For a sequence of \(T\) tokens:
Each token position therefore has a 4096-dimensional residual vector.
For the prompt:
The capital of France is
we can imagine:
The → x₁
capital → x₂
of → x₃
France → x₄
is → x₅
Every layer modifies these vectors.
But because the modifications are residual additions, the computation looks like:
So after many components:
This is an extremely useful mental model.
The final representation is the original token representation plus a long sequence of learned edits.
Attention reads the scratchpad and writes back into it¶
Recall attention:
More precisely, an attention block reads the current residual stream and projects it into Q, K and V spaces.
After attention computes its result, another projection maps that result back into the model dimension:
Then:
So attention does not replace \(X\).
It says something like:
I found useful information elsewhere in the sequence. Let me write that information into the shared state.
This gives attention heads a useful interpretation:
through the residual stream.
A toy example: copying “France”¶
Consider:
The capital of France is
Suppose the residual vector at the final token is initially contains information roughly corresponding to:
current position
grammatical context
expects a noun phrase next
An attention head at is might strongly attend to France.
Its output could write a direction into the residual stream corresponding roughly to:
relevant country = France
So before the head:
and the head computes:
After the residual addition:
Now later components can read \(x'_{is}\) and see both:
expects completion
+
France is the relevant entity
The head didn't have to call the later MLP directly.
It simply wrote information onto the shared scratchpad.
MLPs use the same channel¶
Now imagine the next MLP receives:
An MLP is roughly:
It can detect combinations of features in the residual stream.
Perhaps the current vector contains directions corresponding to:
country = France
relation = capital
factual completion
The MLP may transform that combination into another useful direction:
likely answer = Paris
Its output is again added:
So the computation could look conceptually like:
residual stream:
"we need a factual completion"
↓
attention writes:
"the relevant country is France"
↓
MLP reads both and writes:
"capital-of-France points toward Paris"
↓
later layers refine
↓
unembedding produces high Paris logit
This is much closer to how interpretability researchers often reason about Transformer circuits.
The output layer also reads the residual stream¶
At the end, the model converts the final residual vector into vocabulary logits.
Ignoring normalization details for a moment:
where:
is often called the unembedding matrix.
For token \(v\):
So if some component writes a vector into the residual stream that aligns with:
the Paris logit increases.
This gives us a surprisingly concrete way to think about model computation:
Components write vectors into the residual stream; those vectors eventually push vocabulary logits up or down.
A tiny numerical example¶
Let's shrink the model dimension to:
Suppose the current residual state is:
An attention head writes:
Now:
Then an MLP writes:
Final state:
Suppose the unembedding direction for Paris is:
Then the Paris logit is:
Before the attention and MLP updates, it was:
So two components collaboratively moved the model from:
Paris logit ≈ low
to:
Paris logit ≈ high
by writing different pieces of information into the same vector space.
This explains why circuits can span layers¶
Suppose head 7 in layer 10 writes a feature:
current subject = France
into the residual stream.
An MLP in layer 12 can read it.
An attention head in layer 17 can combine it with information from another token.
An MLP in layer 21 can transform the result again.
Nothing requires those components to be adjacent.
They communicate because the residual stream persists through the network.
Conceptually:
Layer 10 head
│ writes A
▼
RESIDUAL STREAM
│
Layer 12 MLP reads A, writes B
▼
RESIDUAL STREAM
│
Layer 17 head reads B, writes C
▼
RESIDUAL STREAM
│
Layer 21 MLP reads C
This is why the residual stream is so important for mechanistic interpretability.
It is the bus connecting the model's computational components.
Residual connections also help optimization¶
Residual streams were not invented primarily for interpretability.
They make deep networks much easier to train.
Without a residual connection:
Every layer must completely transform the representation passed to the next layer.
With a residual connection:
A layer can initially learn:
and leave the representation mostly unchanged.
It only needs to learn useful corrections.
Gradients also have a direct path backward through the identity connection.
If:
then:
That identity term:
provides a clean route for gradient flow through very deep networks.
This is one reason residual architectures made extremely deep neural networks practical.
Pre-norm Transformers add one wrinkle¶
Many modern Transformers use a structure roughly like:
followed by:
The normalization affects what the component reads, while the result is added back into the persistent residual stream.
So a more accurate picture is:
residual stream
│
├─────── identity path ───────────────┐
│ │
↓ │
norm │
↓ │
attention │
↓ │
output │
└──────────── add ────────────────────┘
↓
residual stream
Then the MLP performs a similar read-transform-add operation.
The exact normalization scheme varies by architecture, but the read/write intuition remains useful.
Why “scratchpad” is useful but imperfect¶
Calling the residual stream a scratchpad can make it sound like there are explicit slots:
dimension 17 = country
dimension 892 = sentiment
dimension 2041 = current owner
Yesterday's lesson warned us that this is usually too simple.
Because of superposition, features are often represented as directions distributed across many dimensions.
So the scratchpad is not like a spreadsheet with named columns.
It's more like a high-dimensional analog workspace.
A component can write:
and another can detect that direction through a learned projection.
Many such feature directions may coexist in the same 4096-dimensional vector.
This leads to a powerful interpretability trick¶
Suppose we want to know when the model begins to “know” that the answer is Paris.
At every layer \(l\), we have a residual vector:
We can project that intermediate vector through the model's unembedding matrix:
Then inspect the Paris logit as depth increases.
Perhaps we see:
Layer 2: Paris rank 18,000
Layer 8: Paris rank 2,400
Layer 14: Paris rank 190
Layer 20: Paris rank 12
Layer 26: Paris rank 2
Layer 32: Paris rank 1
This kind of technique is often called a logit lens.
It asks:
If we interpreted the residual stream right now as though it were the final representation, what answer is it leaning toward?
There are caveats—intermediate representations are not necessarily calibrated for the final unembedding, and normalization matters—but it gives us a window into how predictions develop across layers.
We can go even finer: logit attribution¶
Because residual updates are additive:
and logits are approximately linear in the final residual state:
we can write:
That means we can ask:
How much did this particular attention head's output push the
Parislogit?
If one head writes:
its direct contribution is roughly:
Maybe:
Layer 18, Head 7 +1.4 Paris logit
Layer 20, MLP +2.1
Layer 24, Head 3 -0.3
Layer 27, MLP +1.7
This doesn't completely explain the computation, because components also change what later components will do.
But it gives us a powerful accounting system.
We can literally measure which components are writing in directions that favor particular outputs.
Connect this back to yesterday's sparse features¶
Yesterday we said an SAE might identify a feature corresponding to:
country-capital relationship
Where does that feature live?
Often, what we're analyzing is precisely an activation in the residual stream or another internal activation derived from it.
So the interpretability stack starts to fit together:
RESIDUAL STREAM
↓
messy high-dimensional representation
↓
sparse autoencoder
↓
candidate interpretable features
↓
trace which components
read/write those features
↓
identify circuits
The residual stream gives us the shared medium.
SAEs try to give us a vocabulary for describing what's represented in that medium.
Circuit analysis tries to explain how components manipulate those representations.
The deeper mental model: a shared whiteboard¶
Imagine 64 specialists working on one problem.
Instead of talking directly to one another, they share a giant whiteboard.
Specialist 1 writes:
Relevant entity: France
Specialist 7 notices that and writes:
Question asks for capital
Specialist 19 combines both:
Candidate: Paris
Specialist 31 notices another clue and strengthens it.
Specialist 44 writes:
Paris confidence ↑
Nobody owns the whole solution.
Each specialist:
performs a specialized transformation, then:
The board persists.
That's the residual stream.
And it gives us a much more concrete picture of what a Transformer layer is doing:
The Transformer is not repeatedly replacing its thoughts.
It is progressively editing a shared high-dimensional state.
That perspective will be useful for the next step: looking at what MLPs actually do when they read the residual stream—why the feed-forward network is much more than a generic nonlinear layer, and why it is often described as a kind of learned key-value memory.