Task 5 of 5
A transform earns the name by being reversible. The inverse DFT is the forward one
with two edits: the exponent's sign flips to +, and the whole thing is divided
by n. Both edits are load-bearing, and both are where people go wrong —
forget the 1/n and your signal comes back 256 times too loud; leave the sign
negative and it comes back time-reversed, which is a spectacular way to fail a
test that only checks sample 0.
Summing complex terms means real arithmetic on pairs. With c = cos(angle)
and s = sin(angle), one term of (re + i·im) · (c + i·s) is:
real += re * c - im * s;
imaginary += re * s + im * c;
The shapes line up for free. output: [n, 2] hands back exactly the
[2][n] nested array a kernel wants as input — spectrum[0][k] real,
spectrum[1][k] imaginary — so the forward transform's result drops into the
inverse with nothing in between. The original signal is real, so plane 1 of the round trip
should come back as float noise: that residue is a free correctness check.
output: [256, 2],
taking the [2][256] spectrum — and confirm that transforming
signal and transforming it back recovers all 256 samples.k, and use this.thread.x as the SAMPLE indexreal += re * c - im * s, imaginary += re * s + im * cthis.constants.n — once, at the end1e-3 — all of them shouldThe forward kernel's thread owned a bin and looped over samples. Here the
thread owns a sample and loops over bins, so this.thread.x is
i and the loop variable is k:
const angle = 2 * Math.PI * k * this.thread.x / this.constants.n;Same branch as the forward transform, over the complex product:
const c = Math.cos(angle);
const s = Math.sin(angle);
if (this.thread.y === 0) acc += spectrum[0][k] * c - spectrum[1][k] * s;
else acc += spectrum[0][k] * s + spectrum[1][k] * c;return acc / this.constants.n; — once, on the finished sum, not
inside the loop. Forward does not scale, inverse divides by n; put the 1/n on the wrong
side and the round trip is off by a factor of 65,536.
ifft, and cuFFT documents its own choice per plan — which is why "my round
trip is n times too big" is one of the most-asked FFT questions on every platform. The
sign of the exponent is equally conventional; what is not optional is that the forward and
inverse pair disagree about it.
This page is an interactive exercise — the editor, the GPU runner and your saved progress need JavaScript. The text above is the full brief.