Proving Fourier transform operation in Python

99封情书 提交于 2019-12-24 02:09:08

问题


I have an expression in the time domain

f = -1j*H(t) * exp(-(1j*a+b)*t)

which can be Fourier transformed analytically using known properties (H is the Heaviside step function). The result of this FT operation is

F = (w-a-1j*b)/((w-a)**2+b**2)

where w is frequency.

Now I'm using the tips in this article to do numerical Fourier transform on f in Python, and confirm that I do get the same analytical result F:

import numpy as np
import matplotlib.pyplot as plt

t = np.linspace(-10,10,1e4) # time
w = np.linspace(-10,10,1e4) # frequency

b = 0.1
a = 1

H = lambda x: 1*(x>0) # heaviside function

# function in time
f = -1j*H(t)*np.exp(-(1j*a+b)*t)

# function in frequency (analytical work)
F = (w-a-1j*b)/((w-a)**2+b**2)

hann = np.hanning(len(t))  # hanning window

# function in frequency (numerical work)
F2 = 2/len(t)*np.fft.fft(hann*f)

plt.figure()
plt.plot(w,F.real,'b',label='analytical')
plt.plot(w,F2.real,'b--',label='fft')
plt.xlabel(r'$\omega$')
plt.ylabel(r'Re($F(\omega)$)')
plt.legend(loc='best')

plt.figure()
plt.plot(w,F.imag,'g',label='analytical')
plt.plot(w,F2.imag,'g--',label='fft')
plt.xlabel(r'$\omega$')
plt.ylabel(r'Im($F(\omega)$)')
plt.legend(loc='best')

plt.show()

However Python's FFT function seems to give me something completely wrong. This is evident when F and F2 are plotted.

Edit: Here are the plots...

It's not obvious in these figures, but if you zoom in around the w=-10 and 10 areas, there are small oscillations, possibly due to the fft algorithm.


回答1:


The FFT algorithm computes the DFT, which has the origin (both spatial and in frequency domain) on the first sample. You need to shift your signal (after applying the Hanning window) so that t=0 is the leftmost sample, and after computing the FFT you have to do the inverse shift.

MATLAB has ifftshift and fftshift, which implement those two shifts. NumPy must have similar functions.

Another issue with your code is that you compute the DFT, and plot it at the locations given by the w that you computed, but is unrelated to the actual frequencies at which the DFT is computed.

Here is your code, translated to MATLAB, and fixed to properly compute F2 and w *. I hope this is useful. One thing to note is that your F does not match F2, I am confident that this is not due to an error in F2, but an error in your computation of F. The shapes are similar, but F is scaled differently and mirrored.

N = 1e3;
t = linspace(-100,100,N); % time
Fs = 1/(t(2)-t(1));
w = Fs * (-floor(N/2):floor((N-1)/2)) / N; % NOTE proper frequencies

b = 0.1;
a = 1;

H = @(x)1*(x>0); % Heaviside function

% function in time
f = -1j*H(t).*exp(-(1j*a+b)*t);

% function in frequency (analytical work)
F = (w-a-1j*b)./((w-a).^2+b.^2);

% hanning window
hann = 0.5*(1-cos(2*pi*linspace(0,1,N)));

% function in frequency (numerical work)
F2 = fftshift(fft(ifftshift(hann.*f))); % NOTE shifting of origin

figure

subplot(2,1,1), hold on
plot(w,real(F),'b-')
plot(w,real(F2),'r-')
xlabel('\omega')
ylabel('Re(F(\omega))')
legend({'analytical','fft'},'Location','best')

subplot(2,1,2), hold on
plot(w,imag(F),'b-')
plot(w,imag(F2),'r-')
xlabel('\omega')
ylabel('Im(F(\omega))')
legend({'analytical','fft'},'Location','best')

Footnote:
* I also changed the colors, MATLAB's green is too light.



来源:https://stackoverflow.com/questions/49130327/proving-fourier-transform-operation-in-python

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!