Vision Transformers

In 2020, a simple question upended a decade of convolutional network design: what if an image is just a sentence made of patches? Convolutional neural networks had dominated vision since Image Classification with Deep Networks proved deep hierarchies of local filters could beat hand-crafted features. Detectors like those in Single-Shot Detectors built entire pipelines on convolutional backbones. These backbones had built-in translation equivariance and locality. The Vision Transformer (ViT) discarded convolution almost entirely. It cut an image into fixed-size patches, embedding each patch as a token. The sequence was then fed through a standard Transformer encoder. This was the same architecture that had already conquered language modeling. The stakes are practical, not just aesthetic. Convolutional inductive biases — locality, weight sharing, translation equivariance — are excellent priors when training data is limited. But they also cap the model's ability to exploit huge datasets and huge compute budgets. ViT's bet was different. With enough pretraining data, an architecture with weaker built-in assumptions could work better. Global self-attention from the very first layer could learn better representations than a CNN could. It could also scale more predictably. That bet paid off. ViT and its descendants now back state-of-the-art image classifiers, object detectors, and segmentation models. They also power the vision towers of large multimodal systems like CLIP and vision-language assistants. The core mechanical idea is deceptively simple. Split an image into a grid of patches (say 16×16 pixels). Flatten each patch into a vector, then linearly project it into an embedding space. Add a learnable position encoding, and prepend a special classification token. Run the whole sequence through alternating blocks of multi-head self-attention and feed-forward networks. This is exactly the recipe used for text. No convolution, no pooling, no hand-designed receptive field growth. Every patch can attend to every other patch at every layer. This lets the model build global context immediately. It need not accumulate context gradually across many convolutional layers. This article builds the concept from the ground up. It covers how patch tokenization turns pixels into a sequence. It explains how self-attention lets tokens exchange information. It shows how the architecture is assembled and trained. It explores why it needs so much data or careful regularization to work well. It also examines where it now sits inside real production systems. It closes by pointing toward Self-Supervised Vision, where ViT-style backbones are trained without any labels at all.

Key takeaways
  • ViT treats an image as a sequence of flattened patches, embeds them as tokens, and applies a standard Transformer encoder — no convolutions.
  • Patch tokenization plus a learnable [CLS] token plus positional embeddings turns a 2D image into a 1D sequence a Transformer can consume.
  • Self-attention lets every patch exchange information with every other patch at every layer, giving global receptive field from layer one.
  • ViT has weaker inductive bias than CNNs, so it underperforms them on small datasets but overtakes them with large-scale pretraining.
  • Complexity is quadratic in the number of patches, O(N2d)O(N^2 d) per layer, which motivates efficient variants for high-resolution inputs.
  • ViT backbones now underpin detection, segmentation, and multimodal models, and are the default target for self-supervised pretraining.
The core insight

An image is just a sequence of patch tokens, and a Transformer's global self-attention can learn the spatial structure that convolution used to hard-code.

The idea

A Vision Transformer (ViT) applies the Transformer encoder architecture, originally developed for sequences of word tokens, directly to sequences of image patch tokens. An input image of resolution H×W×CH \times W \times C is partitioned into a grid of non-overlapping patches of size P×PP \times P, producing N=HW/P2N = HW / P^2 patches. Each patch is flattened into a vector of length P2CP^2 C and linearly projected into a DD-dimensional embedding — this projection is called patch tokenization or patch embedding, and it is the entire "vision-specific" part of the architecture. Everything downstream is generic Transformer machinery. Because a Transformer's self-attention is permutation-invariant — it treats its input as an unordered set of tokens — spatial position must be reinjected explicitly. ViT adds a learnable (or fixed sinusoidal) positional embedding to each patch embedding, so the model can, if useful, recover 2D structure such as "this patch is above that one." A special learnable [CLS] token is prepended to the sequence; its output embedding after the final layer is used as the aggregate image representation for classification, analogous to its role in BERT for sentence-level tasks. The heart of the architecture is multi-head self-attention (MHSA). For a sequence of N+1N{+}1 token embeddings (patches plus CLS), each layer computes queries, keys, and values via learned linear maps, then lets every token attend to every other token according to a softmax-normalized similarity of queries and keys. This is fundamentally different from a convolution, which only mixes information within a small, fixed spatial neighborhood and only grows its receptive field by stacking layers. Self-attention gives every layer a receptive field covering the entire image, at the cost of quadratic compute in the number of tokens and the loss of built-in locality and translation equivariance — properties CNNs get for free.

How it works

Step 1 — Patchify. Split the H×W×CH \times W \times C image into N=(H/P)(W/P)N = (H/P)(W/P) non-overlapping P×PP \times P patches. Flatten each into a vector of dimension P2CP^2 C.

Step 2 — Linear patch embedding. Multiply each flattened patch by a learned matrix E∈R(P2C)×DE \in \mathbb{R}^{(P^2C) \times D} to obtain a DD-dimensional token. In practice this is implemented as a single strided convolution with kernel size PP and stride PP — mathematically identical to patch-then-flatten-then-linear, but faster in standard deep learning frameworks.

Step 3 — Prepend CLS token, add positional embeddings. Prepend a learnable vector xclsx_{cls}, then add a learnable positional embedding Epos∈R(N+1)×DE_{pos} \in \mathbb{R}^{(N+1)\times D} elementwise to the (N+1)(N{+}1) tokens.

Step 4 — Transformer encoder. Pass the sequence through LL identical blocks, each consisting of LayerNorm, multi-head self-attention with a residual connection, LayerNorm, and a two-layer MLP (with GELU activation) with a residual connection.

Step 5 — Classification head. Take the final-layer CLS token embedding, apply LayerNorm, and pass through a small MLP (or single linear layer during fine-tuning) to produce class logits. ``` function VisionTransformer(image, params):

# image: H x W x C tensor patches = split_into_patches(image, patch_size=P) # N patches, each PPC patch_embeddings = patches @ E # N x D, E is learned P^2C x D tokens = concat(CLS_token, patch_embeddings) # (N+1) x D tokens = tokens + positional_embeddings # (N+1) x D, elementwise add for layer in 1..L:

# --- Multi-head self-attention sub-block --- normed = LayerNorm(tokens) Q, K, V = normed @ Wq, normed @ Wk, normed @ Wv # each (N+1) x D Q, K, V = split_into_heads(Q, K, V, num_heads=h) # h heads of dim D/h for each head: scores = (Q_head @ K_head^T) / sqrt(D/h) # (N+1) x (N+1) attn_weights = softmax(scores, axis=-1) head_out = attn_weights @ V_head # (N+1) x (D/h) attn_out = concat(all head_out) @ Wo # (N+1) x D tokens = tokens + attn_out # residual connection

# --- MLP sub-block --- normed2 = LayerNorm(tokens) mlp_out = GELU(normed2 @ W1 + b1) @ W2 + b2 tokens = tokens + mlp_out # residual connection cls_final = LayerNorm(tokens[0]) # CLS token row logits = cls_final @ W_head + b_head return logits ``` Every step above is differentiable and trained end-to-end with a standard classification loss (cross-entropy against image labels), typically after large-scale pretraining and then fine-tuning at higher resolution on the target task.

Figure
Vision Transformer pipeline: patches become tokens, tokens pass through stacked encoder blocks
Input image P×P flatten + linear E CLS p1 p2 p3 … pN + positional embeddings Encoder block × L LayerNorm Multi-Head Self-Attention residual LayerNorm MLP (GELU) residual take CLS token LayerNorm + Linear head → class logits

Complexity & correctness

Time complexity. Let NN be the number of patch tokens (plus one for CLS), DD the embedding dimension, and LL the number of encoder layers. Each self-attention sub-block computes QQ, KK, VV projections in O(ND2)O(ND^2), the pairwise attention scores QK⊤QK^\top in O(N2D)O(N^2 D), and the weighted sum with VV in another O(N2D)O(N^2 D). The MLP sub-block, typically expanding to 4D4D hidden units, costs O(ND2)O(ND^2). Summed over LL layers, total time is

O(L(N2D+ND2)).O\big(L (N^2 D + N D^2)\big).

The N2DN^2 D term dominates when the number of patches is large relative to the embedding width — this is the well-known quadratic bottleneck of self-attention. For a 224×224224\times224 image with 16×1616\times16 patches, N=196N = 196, small enough that the ND2ND^2 term (linear projections) often dominates in practice; but at higher resolutions or with smaller patches, NN grows quadratically with image side length (N∝(H/P)2N \propto (H/P)^2), so overall attention cost scales as the fourth power of image resolution — a serious practical constraint that motivates windowed and hierarchical attention variants.

Space complexity. Storing the full attention matrix per head requires O(N2)O(N^2) per layer (before summing over heads it is O(hN2)O(hN^2) split across hh heads of size N×NN \times N each, same asymptotic total), plus O(ND)O(ND) for activations. Memory is dominated by the N2N^2 attention matrices during training when backpropagating through softmax, which is why memory-efficient attention implementations (recomputing rather than storing the full matrix) matter for large images.

Correctness / why it learns the right thing. There is no combinatorial correctness proof for a learned model the way there is for a sorting algorithm; the relevant argument is representational and statistical. Representational sufficiency: self-attention with a residual stream can represent, in principle, any function a convolution can — a convolution is a special case of a sparse, weight-shared attention pattern restricted to a local window with fixed weights. A sufficiently expressive attention layer can therefore learn to emulate local, translation-equivariant filtering if that is what the data demands, and the model additionally has access to genuinely global interactions from layer one. This is a strict superset of representational power, at the cost of a much larger hypothesis space to search. Why more data is needed: because CNNs bake in the assumption "nearby pixels matter most, and the same filter should work everywhere," they need fewer examples to find good filters — the inductive bias substitutes for data. ViT drops that assumption, so early layers must learn from data that nearby pixels are usually more relevant. On small datasets (e.g. ImageNet-1k trained from scratch), ViT underperforms comparable CNNs because it has not seen enough examples to discover these regularities reliably. On large datasets (JFT-300M-scale pretraining, or heavy augmentation/distillation as in DeiT), ViT matches or exceeds CNNs, because the extra capacity that was previously "wasted" relearning locality can instead be spent on patterns convolution could never represent efficiently, such as long-range part relationships. Position embeddings encode 2D structure empirically: since self-attention is permutation-invariant, the only signal telling the model which patch is where is the positional embedding. Empirically, learned positional embeddings in trained ViTs exhibit smooth 2D similarity structure — nearby patches acquire similar embeddings — even though this structure is never explicitly imposed, confirming that the model recovers spatial locality as an emergent, learned property rather than a hard-coded one.

Tradeoffs, stated plainly. ViT trades built-in locality and translation equivariance for flexibility and scalability; it trades better small-data sample efficiency for better large-data ceiling performance; and it trades linear-in-pixels convolutional cost for quadratic-in-tokens attention cost, which becomes the binding constraint at high resolution. None of these are free lunches — the right choice between CNN and ViT backbones still depends on data scale, resolution, and latency budget.

Worked example

Trace a single forward pass on a small, concrete configuration to see the shapes and one attention computation explicitly. Setup: image 32×32×332\times32\times3, patch size P=16P=16, so N=(32/16)×(32/16)=4N = (32/16)\times(32/16) = 4 patches, embedding dimension D=6D = 6 (tiny, for hand tracing), 1 attention head, 1 encoder layer.

StepOperationShape
Patchify4 patches, each 16×16×3=76816\times16\times3 = 768 values4×7684 \times 768
Linear embedmultiply by E∈R768×6E \in \mathbb{R}^{768\times6}4×64 \times 6
Prepend CLSadd CLS row5×65 \times 6
Add positionelementwise add Epos∈R5×6E_{pos}\in\mathbb{R}^{5\times6}5×65 \times 6
LayerNormnormalize each row5×65\times 6
Q, K, Vthree 5×65\times6 times 6×66\times6 weight matrices5×65\times6 each
ScoresQK⊤/6QK^\top / \sqrt{6}5×55\times5
Softmaxrow-normalize scores5×55\times5
Attention outputweights ×V\times V5×65\times 6
Residual + MLP + residualunchanged shape5×65\times6
CLS row extractedrow 01×61\times6
Headlinear to logits (say 3 classes)1×31\times3

Concretely, suppose after LayerNorm the query vector for the CLS token is qcls=[0.1,−0.2,0.4,0.0,0.3,−0.1]q_{cls} = [0.1, -0.2, 0.4, 0.0, 0.3, -0.1] and the four patch key vectors, after the learned WkW_k, happen to be

k1=[0.2,0.1,0.3,−0.1,0.2,0.0],k2=[−0.3,0.4,0.1,0.2,−0.1,0.1],k_1 = [0.2,0.1,0.3,-0.1,0.2,0.0],\quad k_2 = [-0.3,0.4,0.1,0.2,-0.1,0.1],
k3=[0.5,−0.2,0.0,0.3,0.1,−0.2],k4=[0.0,0.0,0.6,−0.3,0.4,0.1].k_3 = [0.5,-0.2,0.0,0.3,0.1,-0.2],\quad k_4 = [0.0,0.0,0.6,-0.3,0.4,0.1].

Computing dot products qcls⋅kiq_{cls}\cdot k_i and dividing by 6≈2.449\sqrt{6}\approx 2.449 gives four raw scores, say {0.06,−0.05,0.09,0.14}\{0.06, -0.05, 0.09, 0.14\} (illustrative values consistent with the vectors above). Softmax over these four numbers (plus the CLS-to-CLS score) produces attention weights that are nearly uniform but slightly favor patch 4 (the largest score), e.g. weights approximately {0.198,0.191,0.198,0.207,0.206}\{0.198, 0.191, 0.198, 0.207, 0.206\} across CLS-self, patch 1–4. The CLS token's new representation is then this weighted average of all five value vectors — meaning even at a single layer, the classification token has already blended information from every patch in the image, something a single convolutional layer with a small kernel could never do. Stacking more layers lets this mixing become increasingly selective, as the query/key projections are trained to sharpen attention toward semantically relevant patches (e.g., patches containing the object rather than background). This trace exposes the mechanism's essence: attention weights are not fixed like a convolution kernel, they are data-dependent, recomputed per image from the learned query/key projections, and they connect arbitrarily distant tokens in one hop.

Common pitfalls & traps

PitfallWhy it happensFix
Training ViT from scratch on a small dataset and expecting CNN-level accuracyViT lacks convolutional inductive bias, so it needs far more data (or strong augmentation/regularization) to learn localityPretrain on large corpora, use heavy augmentation (RandAugment, Mixup) and distillation (as in DeiT), or fine-tune a pretrained checkpoint
Forgetting to interpolate positional embeddings when changing input resolutionPositional embeddings are learned for a fixed NN; a different image size changes NNBilinearly interpolate the 2D grid of positional embeddings to the new patch grid size before fine-tuning
Treating patch size as a free hyperparameter without considering computeSmaller patches increase NN quadratically, blowing up attention cost as O(N2)O(N^2)Choose patch size as a deliberate compute/accuracy tradeoff; consider hierarchical/windowed attention for high resolution
Using only the CLS token embedding when the task needs spatial output (e.g. segmentation)CLS token discards per-patch spatial informationUse the per-patch token outputs (reshaped back to a grid) for dense prediction heads, not just CLS
Ignoring that self-attention is permutation-invariant and skipping positional embeddingsModel then cannot use spatial layout information at allAlways add positional embeddings (learned or fixed) before the first encoder block
Assuming attention maps are literally interpretable as "the model's focus" without checking multiple heads/layersAttention weight in one head at one layer is not the whole story; heads specialize differentlyAggregate or visualize across heads and layers (e.g., attention rollout) before drawing conclusions

Pioneers & history

The Transformer architecture itself originated in sequence modeling for machine translation, replacing recurrence with pure attention. Applying it to raw image patches without convolution required the empirical demonstration that self-attention could match or beat CNNs given sufficient scale — a result that surprised much of the vision community, which had spent a decade optimizing convolutional inductive biases.

Origins · 1 minAlexey Dosovitskiy and how this was discovered
AD
Alexey Dosovitskiy
active researcher, contemporary · Lead author of the original Vision Transformer paper at Google Brain/Google Research, demonstrating that a pure Transformer applied to image patches matches or exceeds convolutional networks when pretrained on sufficiently large datasets

History
2017
— the Transformer architecture is introduced for machine translation, built entirely on self-attention.
2018
— BERT popularizes the [CLS]-token pattern for aggregating sequence representations for classification.
2020
— Dosovitskiy et al. introduce the Vision Transformer (ViT), applying patch tokenization and a pure Transformer encoder directly to images.
2021
— DeiT (Data-efficient image Transformer) shows ViTs can be trained competitively on ImageNet-scale data alone using distillation and augmentation.
2021
onward — hierarchical and windowed variants (Swin Transformer and successors) and hybrid CNN-Transformer designs address the quadratic attention cost for high-resolution and dense-prediction tasks.

Where this matters

ViT backbones now sit inside a wide range of production and research systems. Image classification leaderboards are dominated by ViT and its hierarchical descendants, often pretrained at massive scale and fine-tuned per task. Object detection and segmentation frameworks that once assumed a convolutional backbone (building on the same feature-pyramid ideas discussed in Single-Shot Detectors) now commonly swap in ViT-style backbones, sometimes adapting them to produce multi-scale feature maps for dense prediction. Multimodal systems such as CLIP use a ViT as the image encoder half of a joint image-text embedding space, aligning patch-derived image representations with text embeddings for zero-shot classification and retrieval. Vision-language assistants and generative image models frequently reuse ViT-style patch tokenization as the bridge between pixel grids and Transformer-based reasoning or diffusion architectures. Because ViT's patch-token formulation requires no labels to define — only the raw pixels and their spatial layout — it is also the natural backbone for Self-Supervised Vision methods that learn representations via masked patch prediction or contrastive objectives, extending the same architecture built here far beyond supervised classification.

:::quiz[What is the primary role of the [CLS] token in a Vision Transformer?]

  • It marks the boundary between image patches during tokenization
  • Its final-layer embedding aggregates information for classification ✓
  • It stores the positional embedding for patch zero
  • It is discarded before the encoder and only used at input time

Ask the tutor: How does windowed (hierarchical) attention in models like Swin Transformer reduce the quadratic cost while still capturing global context?

Does ViT completely replace convolutional networks in modern vision systems?

No. CNNs remain competitive and often preferable when training data is limited, latency budgets are tight, or resolution is very high, since convolution's locality and weight-sharing give strong sample efficiency and linear-in-pixels compute. ViT tends to win when large-scale pretraining data is available and compute for quadratic attention is affordable. In practice many state-of-the-art systems use hybrid designs: convolutional stems for early local feature extraction feeding into Transformer blocks, or hierarchical Transformers (like Swin) that reintroduce windowed locality to get the best of both worlds.

Why does ViT need so much more pretraining data than a comparable CNN to reach the same accuracy?

A CNN's architecture already encodes the assumption that nearby pixels are related and that the same filter is useful everywhere in the image — these are called inductive biases, and they act as a strong prior that reduces how much data is needed to find good weights. ViT has no such built-in assumption; self-attention treats all patches symmetrically until training teaches it otherwise. This means ViT's early layers must discover locality-like patterns from data, which requires many more examples, unless techniques like heavy augmentation, distillation, or self-supervised pretraining supply the missing prior more efficiently.

How is a patch actually converted into a token vector mathematically?

Each P×P×CP \times P \times C patch is flattened into a single vector of length P2CP^2 C by reading out its pixel values in a fixed order. This vector is then multiplied by a learned weight matrix EE of shape (P2C)×D(P^2C) \times D, producing a DD-dimensional embedding — an ordinary linear projection, just like a word embedding lookup in NLP but computed via matrix multiplication rather than a lookup table since patch content is continuous, not from a discrete vocabulary. In implementations this linear step is fused with the flattening as a single strided convolution with kernel size and stride equal to PP.

What happens to spatial information if you only ever use the CLS token, for example for image classification?

For pure classification this is fine and intentional: the CLS token is designed to aggregate global information via attention over all patches across all layers, so by the final layer it has effectively summarized the entire image into one vector suitable for a single label prediction. But for tasks requiring spatial output — such as semantic segmentation, depth estimation, or object detection — you instead need the per-patch token embeddings (reshaped back into a 2D grid), since CLS alone discards where in the image any given feature came from.

Is self-attention in ViT actually equivalent in power to convolution, or strictly more powerful?

Self-attention can represent convolution as a special case: a convolution is a linear, weight-shared, spatially local operation, and an attention layer whose weights are constrained to be uniform within a fixed local window and zero elsewhere behaves like a convolution with a box-filter-like mixing pattern. Because ViT's attention weights are unconstrained and computed dynamically from content (via queries and keys) rather than fixed after training, and can connect arbitrarily distant tokens, its representational capacity is a strict superset of a fixed-kernel convolution's — at the cost of needing enough data to actually discover useful patterns within that larger hypothesis space.

Why is the quadratic cost of self-attention such a big practical problem for vision specifically, compared to language?

Text sequences are naturally short — a sentence or paragraph might have a few hundred tokens — but images have far more raw content, and the number of patches NN scales quadratically with image side length (halving patch size, or doubling resolution, roughly quadruples NN). Since attention cost scales as O(N2)O(N^2), vision workloads hit the quadratic wall much faster than typical NLP workloads, which is why high-resolution vision applications often adopt windowed or hierarchical attention (restricting full attention to local windows and only occasionally mixing across windows) rather than plain global ViT attention.

Can ViT be trained without any labels at all?

Yes, and this is an active and increasingly dominant direction. Because ViT's patch-token structure requires no labels to define, only image pixels, it is naturally suited to self-supervised objectives such as predicting masked-out patches from visible ones, or matching augmented views of the same image via contrastive or distillation losses. These approaches, which feed directly into the broader subject of Self-Supervised Vision, often produce representations that transfer as well as or better than fully supervised pretraining, without requiring any labeled dataset at all.

Before this

Where this leads