The single most important operation in this branch. Recognising a convolution turns an double loop into .

Recognising one

You have a convolution whenever the answer at index sums over all pairs of indices combining to :

ProblemCombination
Polynomial multiplication
”Number of ways to get sum from two sets”
Count pairs at distance (reverse one array)
String matching with wildcardscorrelation
Counting subsequence patterns
Multiplying big integers with carries
Counting XOR pairs
Counting AND/OR pairs /
Counting gcd pairs — a Dirichlet convolution

Which transform

Combining ruleTransformCost
FFT / NTT
(cyclic)FFT of length exactly
FWHT
(OR)subset-sum zeta/Möbius
(AND)superset-sum zeta/Möbius
, disjointsubset convolution (ranked SOS)
Dirichlet convolution
prefix sums
, max-plus, convex inputsMinkowski sum
, max-plus, generalno known subquadratic algorithm

The transform-based ones all share the same three-step shape:

transform(a);  transform(b);
for i: c[i] = a[i] * b[i];
inverse_transform(c);

Only the transform differs. That structural uniformity is worth internalising.

The FFT route

vector<long long> multiply(vector<long long> a, vector<long long> b) {
    int need = a.size() + b.size() - 1, n = 1;
    while (n < need) n <<= 1;
    vector<cd> fa(a.begin(), a.end()), fb(b.begin(), b.end());
    fa.resize(n); fb.resize(n);
    fft(fa, false); fft(fb, false);
    for (int i = 0; i < n; i++) fa[i] *= fb[i];
    fft(fa, true);
    vector<long long> res(need);
    for (int i = 0; i < need; i++) res[i] = llround(fa[i].real());
    return res;
}

Pad to a power of two at least ; padding to less causes cyclic wraparound.

Precision and modulus

SituationMethod
Small integer coefficients, exact neededNTT mod 998244353
Answer mod an arbitrary prime3 NTT primes + CRT, or splitting
Real coefficientscomplex FFT
Large integers, no modulussplit each coefficient into 15-bit halves; 4 transforms
Two real sequences at oncepack them as real and imaginary parts — halves the work

double FFT precision

Error grows roughly as . With and coefficients up to , plain complex FFT loses the low bits. Use NTT, or split coefficients.

Convolution without a transform

Sometimes the structure makes it cheap:

  • Sparse inputs — if has non-zeros, direct evaluation is , better than FFT when is small.
  • Short inputs — below , the loop beats FFT’s constant factor.
  • Convex max-plus — merge the difference sequences in .
  • One input is a prefix/suffix pattern — prefix sums suffice.

Multi-dimensional convolution

Transform along each axis in turn. A 2D convolution of an grid is — used for image filtering and for counting 2D patterns.

The general lesson

Convolution is the bridge between counting problems and fast algorithms. When a problem says “count the ways to combine one thing from each of two sets”, write down the generating function; the answer is a coefficient of a product, and the product is a convolution.

See Generating Functions for the counting side and FFT and NTT for the computation.

See also: FFT and NTT · FWHT · SOS DP