# How do I calculate the correct amplitudes of a discrete Fourier transform (DFT)?

I have a set of samples values in time domain. I know they are uncorrelated and I have to extract the correct amplitudes. However, the values are only ~88% of what they should be.

As a test see the minimal working example in R below. I think it can be understood even if you are not familiar with the language. I generate the data uncorrelated data with rnorm() and then apply fft(). As a consistency check I show that Parseval's theorem is fulfilled, which it is. Is there anything I am not aware of?

MWE:

# dt <- 0.01 # time stesp
nSteps <- 100000 # Number of time steps
# df <- 1/(nSteps*dt) # frequency resolution

# t <- 0:(nSteps-1)*dt #
y <- rnorm(nSteps, mean=0, sd=1) # generate uncorrelated data. Should result in a white noise spectrum with sd=1
y_sq_sum <- sum(y^2)

# We ignore cutting to the Nyquist frequency.
# f <- 0:(nSteps-1)*df
fft_y <- abs(fft(y))/sqrt(length(y))
fft_y_sq_sum <- sum(fft_y^2)

print(paste("Check for Parseval's theorem: y_sq_sum = ", y_sq_sum, "; fft_y_sq_sum = ", fft_y_sq_sum, sep=""))

print(paste("Mean amplitude of my fft spectrum: ", mean(fft_y)))
print(paste("The above is typically around 0.88, why is it not 1?"))
$$$$

• fft_y <- abs(fft(y))/sqrt(length(y)) -- All fft implementations perform some form of normalization -- they usually divide by 1, by $N$, or by $\sqrt{N}$. Have you verified what R's fft` does? – MBaz Oct 10 '20 at 14:37
• @MBaz this is exactly why I checked that Parseval's theorem is fulfilled. The documentation says: When z is a vector, the value computed and returned by fft is the unnormalized univariate discrete Fourier transform of the sequence of values in z. – Christian Oct 10 '20 at 15:05