FFT中从频率到角频率的奇怪行为

信息处理 fft Python 自由度 scipy
2022-02-27 10:48:52

我编写了一个代码来使用 scipy.fft代码如下:f=50.0

import numpy as np
from scipy.fft import fft, fftfreq, fftshift
import matplotlib.pyplot as plt

T = 10
dt = 0.001
f = 50.0 

x = np.arange(0.0, T, dt)
y = np.exp(1.j * 2 * np.pi * f * x)

xf = fftfreq(len(x), dt)
xf = fftshift(xf)

yf = fft(y)
yf = fftshift(yf)

plt.plot(xf, 1.0/len(x) * yf, label='yf')
plt.plot(xf, 1.0/len(x) * np.abs(yf), label='abs(yf)')
plt.xlabel('f')
plt.legend()
plt.show()

计算的输出是具有单峰的频谱,对于 yf 及其绝对值(完全重叠)都以频率为中心: f=50.0

现在我不使用频率,而是假设使用角频率ω=50.0

import numpy as np
from scipy.fft import fft, fftfreq, fftshift
import matplotlib.pyplot as plt

T = 10
dt = 0.001
omega = 50.0 

x = np.arange(0.0, T, dt)
y = np.exp(1.j * omega * x)

xf = fftfreq(len(x), dt)
xf = fftshift(xf)

yf = fft(y)
yf = fftshift(yf)

plt.plot(2 * np.pi * xf, 1.0/len(x) * yf)
plt.plot(2 * np.pi * xf, 1.0/len(x) * np.abs(yf))
plt.show()

在图中,我将 xf 乘以以将频率转换为角频率当然,这对应于与第一个示例不同的频率,但我预计会有类似的行为。在这种情况下 yt 具有一种分散的形状,虽然它的绝对值非常宽泛,但它没有被归一化并且在处不是完美的峰值,但它略微移​​动到2πfωf=ω2πω=50.050.26

在此处输入图像描述

有人可以给我一些关于这种意外行为的解释吗?如果我必须使用来自复杂计算的原始数据,以角频率表示,我如何从第二个程序中获得可靠的结果?ω

1个回答

这可能是这个论坛上被问到最多的一个问题。几个小时前有人问并回答了一个类似的问题:从数学角度看频谱泄漏

您的期望是错误的:如果 FFT 网格上的复指数频率(即采样率的整数倍除以 FFT 长度),您只会得到频谱狄拉克脉冲。在您的情况下,您有,因此您的 FFT bin 间距为 0.1 Hz。50 Hz 是 0.1Hz 的整数倍,但不是,因此能量将分散到相邻的 bin 上。NFFT=10000Fs=100050/(2π)

另一种看待它的方式:DFT 假设时间信号是周期性的,具有 FFT 长度。由于您的指数在一个 FFT 帧内没有整数个周期,因此周期性重复会在帧边界处产生不连续性