matlabfftdft

Why N point FFT of a undersampled signal in time domain is worse than only a N point FFT of the time domain signal (Not resampled)


I am trying to understand what happens when I try to reconstruct the spectrum of a signal with fewer samples. I tried 2 approaches. I resample the time domain signal based on the number of samples (N) I need and then took an FFT. In the second approach, I just did an N point FFT in which, as MATLAB says, the samples after N are ignored. Surprisingly, the second approach gives a good result. I don't understand why. For the ground truth, I simulate the time domain signal using a Gaussian-shaped frequency spectrum.

My MATLAB program is given below. You can change the value of N and see the results. Also you can change the interpolation method for the resampled signal case. I did all types of checks and I think the N point FFT performs better. However, one would think that the resampled signal should performed better when a FFT is applied.

clear;
close all;
% Simulation of ground truth
n = 512;

[sig_a, sig_f] = DS_simulator(10^(Inf/20), 1, 5, 0.2, n, 7.5); % sig_a is the time domain signal with 512 points and sig_f is the Gaussian spectrum from which sig is derived



figure; plot((abs(sig_f).^2)); % Original spectrum 



%% Analysis


N = 256; %Number of fft points

idx = 1:n;
idxq = linspace(min(idx), max(idx), N);
sig_resampled = interp1(idx, sig_a, idxq, 'cubic'); % resampling the signal

figure; plot(1:1:n, abs(sig_a)); hold on; plot(1:n/N:n, abs(sig_resampled), '*'); % signal and resampled signal


sig_resamp_doppler = 1/N .* abs(fftshift(fft(sig_resampled, N))).^2; % FFT of resampled signal
sig_doppler = 1/N .* abs(fftshift(fft(sig_a, N))).^2; % FFT of original signal



figure; plot(abs(sig_doppler)); hold on;  plot(abs(sig_resamp_doppler)); % Reconstructed spectrum 

The code of ground truth signal generation whose spectrum is a Gaussian shape with mean as mu and standard deviation as sigma

function [data, data_f] = DS_simulator(SNR, m0, mu, sigma, n, v_amb)


vel_axis = linspace(-v_amb, v_amb, n);

X = rand(1, n);
Theta = 2 .* pi * rand(1, n);

if sigma < 0.02
    [~, idx1] = min(abs(vel_axis - mu));
    S = dirac(vel_axis - vel_axis(idx1)); 
    idx = S == Inf;
    S(idx) = 1;
else
    S = m0/sqrt(2*pi*sigma^2) * exp(-(vel_axis - mu).^2/(2*sigma^2));
end


N = sum(S) ./ (n .* SNR); % Noise Power

P = -(S + N) .* log(X); % Power spectrum 
data_f = sqrt(P);



data = ifft(fftshift(sqrt(n) .* sqrt(P) .* exp(1j .* Theta)));% complex time domain signal 


end

Solution

  • Your data has very high frequencies. Here I plot the real and imaginary components as two separate signals: plot of OP's data

    Resampling this signal at a lower sampling frequency will introduce aliasing, you'll get a very different signal that no longer looks like the original one.

    If you plot the magnitude, all you see is the envelope. Aliasing does not affect the envelope much, hence your plots do not show the problem.