DTFT是离散时间非周期信号的傅里叶变换,由于其频域曲线是连续周期的,计算机无法处理,所以用冲击函数对其频谱在频域进行采样,得到时域和频域都离散的信号,这类过程叫做DFT。写出DFT的公式我们可以看到,完整的求出信号的DFT需要计算N*N次乘法和N*(N-1)次加减法,所以有大牛又提出了FFT算法简化计算过程,加快计算速度。
matlab提供的fft算法有几点比较关键:
为防止频谱泄漏,做FFT选取的点数NFET(也就是选取的时间段)最好是信号周期的整数倍M,否则fft后的信号幅度小于真正的信号幅度。
NFET*Ts = M*Tsig,但最好也要小于信号长度,否则fft会帮你自动补零,致使振幅谱中出现很多其他成分,这是加零造成的,其振幅由于加了多个零而明显减小。
输出的频谱图的频率分辨率为Fs/NFET,所以NFET越大,波形越逼真;
频谱关于中间位置对称,只需要观察 0:NFET/2(NFET/2+1个点);
MATLAB中FFT的频谱,应该看幅值;
X轴频率点的设置:采样频率为Fs,频谱图显示的最高频率为Fs/2(奈奎斯特率):X轴频率点:(0:NFET/2)*Fs/NFET;
复数幅值修正:假设原始信号的幅度为A,那么FFT结果的每个点(除了第一个点直流分量之外)的模值就是A的N/2倍。而第一个点就是直流分量,它的模值就是直流分量的N倍。所以在做完fft之后,还要进行幅值修正;
所以,为了不补零而又希望频率分辨率足够,一般希望NFET足够接近N,但又不大于。
%%fft_analysis
clear all;
clc;
fs = 1000; %%sampling frequency
N = 100; %%point number of signal; length of signal;
NFET = 100; %% NFET point DFT;
t = (0:N-1)/fs; %% x axis; samples location of signal
y = 0.5*sin(2*pi*20*t)+sin(2*pi*50*t); %% y axis; samples value of signal
x = fft(y,NFET); %%NFET = select how much data point to fft
mag = abs(x)/NFET*2;
f = (0:NFET-1)*fs/NFET;
plot(f(1:NFET/2),mag(1:NFET/2));
grid on;