我不明白为什么ifft(fft(myFunction))和我的函数不一样。它似乎是相同的形状,但是2的因子(忽略常数y偏移)。我可以看到的所有文档都说fft没有做一些规范化,但ifft应该照顾它。下面是一些示例代码 - 你可以看到我已经提到了2的因素给了我正确的答案。感谢您的帮助 - 它让我疯狂。
import numpy as np
import scipy.fftpack as fftp
import matplotlib.pyplot as plt
import matplotlib.pyplot as plt
def fourier_series(x, y, wn, n=None):
# get FFT
myfft = fftp.fft(y, n)
# kill higher freqs above wavenumber wn
myfft[wn:] = 0
# make new series
y2 = fftp.ifft(myfft).real
# find constant y offset
myfft[1:]=0
c = fftp.ifft(myfft)[0]
# remove c, apply factor of 2 and re apply c
y2 = (y2-c)*2 + c
plt.figure(num=None)
plt.plot(x, y, x, y2)
plt.show()
if __name__=='__main__':
x = np.array([float(i) for i in range(0,360)])
y = np.sin(2*np.pi/360*x) + np.sin(2*2*np.pi/360*x) + 5
fourier_series(x, y, 3, 360)
答案 0 :(得分:5)
当您执行myfft[wn:] = 0
时,您将删除一半频谱。负频率是阵列上半部分的频率,是必需的。
你有第二个软糖可以得到你的结果,这个结果是真实的部分找到y2:y2 = fftp.ifft(myfft).real
(fftp.ifft(myfft)
由于光谱中的不对称而具有不可忽略的虚部。) / p>
使用myfft[wn:-wn] = 0
代替myfft[wn:] = 0
进行修复,然后删除软糖。所以固定代码看起来像:
import numpy as np
import scipy.fftpack as fftp
import matplotlib.pyplot as plt
def fourier_series(x, y, wn, n=None):
# get FFT
myfft = fftp.fft(y, n)
# kill higher freqs above wavenumber wn
myfft[wn:-wn] = 0
# make new series
y2 = fftp.ifft(myfft)
plt.figure(num=None)
plt.plot(x, y, x, y2)
plt.show()
if __name__=='__main__':
x = np.array([float(i) for i in range(0,360)])
y = np.sin(2*np.pi/360*x) + np.sin(2*2*np.pi/360*x) + 5
fourier_series(x, y, 3, 360)
在尝试进行信号处理时,确实值得关注您正在创建的临时数组。总是有一些线索可以指出你应该解决的问题。在这种情况下,你采取实际部分掩盖了问题,使你的任务更加困难。
只是添加另一个快速点:有时采取结果数组的实际部分是正确的事情。通常情况下,您最终得到信号输出的虚部,这恰好是反FFT输入中的数值误差。通常,这表现为非常小的虚数值,因此实际部分基本上是相同的数组。
答案 1 :(得分:4)
您正在查杀0
和-wn
之间的负频率。
我认为您的意思是为myfft
以外的所有频率设置0
至[-wn, wn]
。
更改以下行:
myfft[wn:] = 0
为:
myfft[wn:-wn] = 0