fftshift有什么用?MATLAB做FFT后为什么还要fftshift?

本文探讨了在MATLAB中进行FFT分析时,为何有时需要使用fftshift函数,有时则不需要。fftshift用于将零频分量移动到数组中心,以便观察[-fs/2,fs/2]的频谱。对于实序列,由于频谱混叠,通常需要fftshift来查看完整频谱;而对于复序列,由于没有负频率,直接使用FFT即可查看[0,fs]的频谱,无需fftshift。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

文章仅为个人理解,不足之处敬请指正

在用MATLAB做FFT分析信号的时候,为什么有时候需要fftshift,有时候又不需要,今天仔细理了理,做个总结记录。

首先,fftshift的用法:
                           Y = fftshift(X)
                           Y = fftshift(X,dim)
作用:交换行向量的左右两半部分。
在FFT里的作用:通过将零频分量移动到数组中心

为什么要在FFT之后用到fftshift呢?

我觉得这个问题可以从采样定律的角度来说。以基带实信号为例,我们都知道时域的以 f s f_s fs采样就是频域以 f s f_s fs平移延拓,因为采样之后的信号的频谱会在 f s / 2 f_s/2 fs/2产生混叠,所以实信号采样率 f s / 2 f_s/2 fs/2要大于等于带宽,即 f s ≥ 2 B f_s≥2B fs2B,如下图。在这里插入图片描述
MATLAB在对序列做FFT的时候,相当于是取了频谱上 [ 0 , f s ] [0,f_s] [0,fs]的部分,由于频谱是按 f s f_s fs周期延拓,所以 [ f s / 2 , f s ] [f_s/2,f_s] [fs/2,fs]部分的频谱与 [ − f s / 2 , 0 ] [-f_s/2,0] [fs/2,0]部分的一样,如果你想看 [ − f s , f s ] [-f_s,f_s] [fs,fs]部分(上图红框部分),就需要做fftshift,将零频分量移到序列中间,下面看一个例子。

close all; clear; clc;
fs = 300;            %采样率大于200
t = 0:1/fs:1;        %定义采样点
s = sin(2*pi*100*t)+cos(2*pi*40*t);  %采样后的信号序列

%---------[0,fs]的频谱---------
F1 = fft(s);                %fft
f1 = linspace(0,fs,length(t));   %频谱横轴
subplot(211);plot(f1,abs(F1));xlabel('f');ylabel('幅度');title('看[0,fs]');

%---------[-fs/2,fs/2]的频谱---------
F2 = fftshift(fft(s));                %fft
f2 = linspace(0,fs,length(t))-fs/2;   %频谱横轴
subplot(212);plot(f2,abs(F2));xlabel('f');ylabel('幅度');title('看[-fs/2,fs/2]');

结果如下:在这里插入图片描述

所以,fftshift是为了看 [ − f s / 2 , f s / 2 ] [-f_s/2,f_s/2] [fs/2,fs/2]部分频谱而需要的操作,如果只是看 [ 0 , f s ] [0,f_s] [0,fs]的频谱,就不需要了。

上面只是实序列的情况,然而我们仿真实验更经常用到的是复序列,下面谈谈复序列的情况。
复序列没有负频率,采样率只要大于带宽即可,根据上面的讲解很容易理解这点,在这里插入图片描述

上图可以看出来,只要 f s ≥ B f_s≥B fsB,频谱就不会混叠。所以就不会去看 [ − f s / 2 , f s / 2 ] [-f_s/2,f_s/2] [fs/2,fs/2]的频谱,也就不会用到fftshift了。

close all; clear; clc;
fs = 300;            %采样率大于100
t = 0:1/fs:1;        %定义采样点
s = exp(1j*2*pi*100*t)+exp(1j*2*pi*40*t);  %采样后的信号序列

%---------[0,fs]的频谱---------
F1 = fft(s);                %fft
f1 = linspace(0,fs,length(t));   %频谱横轴
plot(f1,abs(F1));xlabel('f');ylabel('幅度');title('看[0,fs]');

%---------[-fs/2,fs/2]的频谱---------
%原本就没有负频率,这儿也就没意义了
% F2 = fftshift(fft(s));                %fft
% f2 = linspace(0,fs,length(t))-fs/2;   %频谱横轴
% subplot(212);plot(f2,abs(F2));xlabel('f');ylabel('幅度');title('看[-fs/2,fs/2]');

在这里插入图片描述

### MATLAB 中 `fft` 和 `fftshift` 函数的用法及区别 #### 1. 傅里叶变换 (`fft`) 的基本概念 快速傅里叶变换 (FFT) 是一种高效的算法,用于计算离散傅里叶变换 (DFT)[^1]。在 MATLAB 中,`fft` 函数实现了这一过程。对于长度为 N 的输入向量 x,`fft(x)` 返回一个同样长度为 N 的复数向量 y。 ```matlab % 创建一个简单的正弦波信号 t = linspace(0, 1, 1000); f = 5; % 频率设为5Hz signal = sin(2*pi*f*t); % 对该信号执行FFT操作 Y_fft = fft(signal); ``` 此代码片段展示了如何创建一个简单的时间域信号并对其进行 FFT 变换[^4]。 #### 2. `fftshift` 的功能介绍 当应用 `fft` 后,默认情况下频率范围是从 0 到 fs(采样频率),这使得负频率位于频谱末端而不是中心位置。为了使可视化更直观以及物理意义上更加合理,可以使用 `fftshift` 来调整输出顺序,从而将 DC 组件移至频谱中央,并相应地重排其他组件的位置[^3]。 ```matlab % 应用fftshift以获得更好的视觉效果 Y_shifted = fftshift(Y_fft); % 计算对应的频率轴 N = length(t); % 获取样本数量 Fs = 1/(t(2)-t(1)); % 计算采样速率 Frequencies = (-Fs/2 : Fs/N : Fs/2-Fs/N)'; ``` 上述例子中,在进行了 FFT 处理之后立即调用了 `fftshift` 函数来改善显示结果[^5]。 #### 3. 关键差异总结 - **默认行为**: 当仅使用 `fft()` 而不加任何额外处理时,得到的结果是以零为中心展开但在数值上从最低到最高排列; - **经由 `fftshift` 修改后的版本**: 它会把原本处于两端的低频成分集中放置于数组中部附近,形成对称分布的形式,便于观察实际存在的负频率分量[^2]; 因此,在大多数应用场景下推荐先一次 `fftshift` 再绘制图形,这样可以获得更为清晰易懂的频谱图像。
评论 11
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值