← Concept library

NLP Foundations

Cosine Similarity vs Dot Product

Two near-identical looking formulas that answer different questions, one measures direction alone, the other measures direction and magnitude together, and picking the wrong one silently breaks a search or ranking system.

beginner · 6 min read

Every embedding-based search, recommendation, or clustering system rests on one small formula, and there are two candidates that look almost the same but behave differently the moment vector magnitudes vary.

The two formulas

dot_product(a, b) = sum_i  a_i * b_i

cosine_similarity(a, b) = dot_product(a, b) / (norm(a) * norm(b))

Cosine similarity is the dot product of the two vectors after each has been normalised to unit length. That normalisation is the entire difference: cosine similarity measures only the angle between two vectors, ignoring how long either one is. Dot product measures angle and magnitude together, so a vector with a larger norm can win a dot-product ranking even when it is less directionally aligned than a shorter competitor.

Which one to use, and why

The choice is not arbitrary, it follows from whether magnitude carries information you want or noise you want to discard. Attention (see attention-mechanism) uses raw, scaled dot products between queries and keys, QK^T / sqrt(d_k), precisely because magnitude is informative there: a key vector with larger norm can represent a token "shouting" for attention, and that signal is meant to influence the score, not be normalised away.

Semantic search and sentence similarity (see embeddings-semantic-search, sentence-embeddings-and-pooling) typically use cosine similarity instead, because the question being asked is "are these about the same thing", not "which one was expressed more forcefully or verbosely". Embedding norm often correlates with incidental factors like token frequency or generic phrasing rather than topical relevance (see embedding-space-geometry-anisotropy), so discarding magnitude tends to produce more meaningful rankings for this task.

There is a practical shortcut worth knowing: if every vector in a collection is pre-normalised to unit length, dot product and cosine similarity are mathematically identical, since norm(a) = norm(b) = 1 makes the denominator vanish. This is why many vector databases normalise embeddings once at indexing time and then run plain dot-product search, which is cheaper, without losing the cosine-similarity semantics.

When it falls down

  • Cosine similarity discards magnitude information that can be meaningful. In embedding spaces where norm correlates with confidence, frequency, or specificity, throwing that away removes a real signal, not just noise.
  • Dot product rankings can be dominated by a single high-norm outlier. In a raw, non-normalised embedding collection, one unusually long vector can rank near the top of every query regardless of actual semantic relevance, a common silent bug in nearest-neighbour search.
  • Neither metric is a learned notion of similarity. Both assume the embedding space's existing angular or Euclidean structure already reflects "meaning" well; if the space is anisotropic, both inherit that distortion.
  • Approximate nearest-neighbour indexes are metric-specific. Libraries like HNSW or IVF often natively support one metric, and emulating the other correctly requires disciplined normalisation at index-build time; getting this wrong produces silently degraded (not obviously broken) search results.

Further reading

Sign in to save and react.
Share Copied