C FFTW库:验证傅里叶变换导数属性

C FFTW库:验证傅里叶变换导数属性,c,signal-processing,fft,fftw,C,Signal Processing,Fft,Fftw,我正在尝试验证与fftw库的这种关系: 因此,我选择f为高斯,计算其导数的傅里叶变换,并将其与高斯乘以ik的傅里叶变换进行比较。以下是我得到的: 这很奇怪,特别是因为高斯导数(即红色导数)的傅里叶变换图在原点不是0,而应该是(我用解析图检查) 代码对我来说似乎没问题,不管怎样,它就在这里(我使用的是C): intmain(){ int i,N=100; 双v[N],x[N],k[N/2+1],vd[N]; 双dx=2*pi/N,dk=2*pi/(N*dx),tmp; fftw_复合体*out

我正在尝试验证与fftw库的这种关系:

因此,我选择f为高斯,计算其导数的傅里叶变换,并将其与高斯乘以ik的傅里叶变换进行比较。以下是我得到的:

这很奇怪,特别是因为高斯导数(即红色导数)的傅里叶变换图在原点不是0,而应该是(我用解析图检查)

代码对我来说似乎没问题,不管怎样,它就在这里(我使用的是C):

intmain(){
int i,N=100;
双v[N],x[N],k[N/2+1],vd[N];
双dx=2*pi/N,dk=2*pi/(N*dx),tmp;
fftw_复合体*out;
fftw_计划正向、反向;
out=(fftw_复合体*)fftw_malloc(尺寸)(fftw_复合体)*(N/2+1));
正向=fftw\U平面图\U dft\U r2c\U 1d(N,v,out,fftw\U估算值);
反向=fftw_平面图_dft_c2r_1d(N,out,vd,fftw_估计值);
//初始化数组
对于(i=0;i

有谁能告诉我我做错了什么吗?

导出高斯函数的离散化信号应该是:

        x[i] = dx*i;
        v[i] = -2*x[i]*exp( -pow( x[i], 2) );
然而,离散傅里叶变换对应于周期信号的傅里叶变换。实际上,下面的离散化函数被写为正弦波的无限加权和

因此,当应用DFT时,上述离散化信号对应于高斯函数导数的周期性一半。事实上,它的平均值(零频率)不是零,因为所有的值都是负值

要模拟高斯(或“有限”范围的任何其他信号)的导数,必须覆盖信号的整个范围。因此,必须选择
dx
,以便
dx*N>>σ
,其中
σ
是高斯分布的标准偏差。必须涵盖函数的所有支持,包括导数的正面

你能试试这样的东西吗

        double sigma=dx*N*0.1;
        x[i] = dx*i-dx*(N/2);
        v[i] = -2*x[i]*exp( -pow( x[i]/sigma, 2) );
由于标准偏差的值,必须留有标度


DFT对于非周期函数仍然有用,但非周期函数将通过使用。这里观察到的是,应用一个矩形窗口,周期化,然后推导与应用一个矩形窗口,最后周期化的推导不同。虽然都是线性的,但这些运营商不会通勤

请在您的问题中直接发布(相关)代码,而不是代码图像的链接。请注意,虽然这种关系适用于傅里叶变换,但离散傅里叶变换并不那么简单。是的,原则上您是对的,但我检查了(例如这里:)它应该仍然有效。这根本没有提到DFT。一个明显的错误是
k
只有大小
N/2+1
,但是你初始化它就像它有大小
N
N
for
循环中应该
N/2
)设置
sigma=dx=1
应该很好,使计算更容易。我从中得到了一个很好的DFT,我同意你关于周期性的论点,事实上我应该变换一个在“盒子”的极端具有相同值的函数。问题是,据我所知,FFTW的工作方式是,输出阵列的第一个元素与频率原点相关联,因此每当我变换一个不是从原点开始的信号时,我就会遇到问题(顺便说一句,如果你知道如何解决这一问题,那就太好了)。我试过用高斯函数,它从原点开始,以方框的一半为中心,但这些曲线图还是很不一样。@Mike:事实上,这是比矩形窗口更精细的窗口背后的想法。大多数窗口的特征值在边缘附近趋于零,以便恢复连续的周期信号,并避免引入人为的不连续性,从而污染导数的估计。事实上,某些窗口的边缘具有零导数,因此即使周期信号的一阶导数也保持平滑。您可以尝试应用Tukey窗口@米肯:这里不需要窗口功能。您需要确保在您的
v[i]
中有完整的高斯分布,原点在
v[0]
,周期为
v[i]
v[i+size]
应从
-1
-size/2
填充
i
。通过这种方式,您可以将整个内核放入信号中,并且仍然具有DFT所需的原点。如果
v
足够大,高斯分布不会在任何地方引入任何间断。
        double sigma=dx*N*0.1;
        x[i] = dx*i-dx*(N/2);
        v[i] = -2*x[i]*exp( -pow( x[i]/sigma, 2) );