06 — Foundations

Feed-Forward Networks#

SwiGLU · GELU · ExpansionMathematical 1 min read
◆ The PatternThe per-token MLP after every attention layer

After attention mixes information across tokens, the feed-forward network (FFN) processes each token independently. It expands to a higher dimension, applies a nonlinearity, and projects back down. Much of the model’s factual recall appears to live here (Geva et al. 2021).

FFN(x) = W₂ · σ(W₁x + b₁) + b₂ where W₁ ∈ ℝ^(d × 4d)
Classic design: expand 4×, activate, contract. About 2/3 of transformer parameters live here.
SwiGLU(x) = (W₁x ⊙ Swish(W_gate·x)) · W₂ where W₁,W_gate ∈ ℝ^(d × ⅔·4d)
Gated variant used in LLaMA, Mistral, Gemma. ⅔ factor keeps parameter count equal to standard 4d expansion.

SwiGLU consistently outperforms ReLU and GELU. The gating mechanism lets the network learn to suppress/amplify features multiplicatively — more expressive than additive bias alone.

In Llama 2 70B the feed-forward layers hold about 56B of its 69B parameters. They act as massive key-value memories: keys are W₁ rows, values are W₂ columns.
Interactive — activation functions comparison

Python — SwiGLU FFN#

Pattern bridge: The MLP after attention stores factual knowledge — the model’s memory bank. Like activation functions that add non-linearity after linear attention.
Worked example

With d = 4,096, a classic feed-forward layer with a 4d hidden size has 134,217,728 parameters. SwiGLU uses three matrices instead of two, so it shrinks the hidden size to two thirds of 4d to keep the count equal: 134,221,824. LLaMA rounds that hidden size to 11,008 for hardware efficiency, giving 135,266,304.

Where it misleads
  • Gated variants win in experiments, but the explanation is thin; Shazeer (2020) attributes the success to “divine benevolence”.
  • Most of a dense model’s parameters sit here, and so does much of its factual recall (Geva et al. 2021) — which is why editing a fact can have side-effects.
  • Feed-forward size and depth trade off; parameter count alone does not say which shape is better.
In code
d = 4_096
classic = 2 * d * (4 * d)                       # W1 and W2 with a 4d hidden layer
swiglu_ideal = 3 * d * round(2 / 3 * 4 * d)     # three matrices at 2/3 of 4d keep the count equal
swiglu_llama = 3 * d * 11_008                   # LLaMA-7B rounds the hidden size to 11,008
Python, in your browser — edit the code and run it again

Assumes import numpy as np. Configurations named after real models use their published shapes; other numbers are made up or simulated, as the comments say.

The same idea with a library
import torch, torch.nn as nn, torch.nn.functional as F

class SwiGLU_FFN(nn.Module):
    def __init__(self, d_model, expansion=8/3):
        super().__init__()
        hidden = int(d_model * expansion)
        self.w1 = nn.Linear(d_model, hidden, bias=False)
        self.w_gate = nn.Linear(d_model, hidden, bias=False)
        self.w2 = nn.Linear(hidden, d_model, bias=False)

    def forward(self, x):
        return self.w2(self.w1(x) * F.silu(self.w_gate(x)))
Sources
  • N. Shazeer, “GLU Variants Improve Transformer”, arXiv:2002.05202, 2020
  • M. Geva, R. Schuster, J. Berant & O. Levy, “Transformer Feed-Forward Layers Are Key-Value Memories”, EMNLP, 2021
  • H. Touvron et al., “LLaMA: Open and Efficient Foundation Language Models”, arXiv:2302.13971, 2023

Last reviewed October 2026 · How this site checks its content · Report a mistake

Linked from 1
← Previous
Multi-Head Attention
Open in the full reader, with the topic sidebar