通过对 FFT 结果进行共轭来使用 FFT 进行 IFFT

Posted

技术标签:

【中文标题】通过对 FFT 结果进行共轭来使用 FFT 进行 IFFT【英文标题】:IFFT using FFT by taking conjugate of the FFT result 【发布时间】:2014-04-10 12:34:45 【问题描述】:

我正在使用 C 语言在 8 位 pic 微控制器上进行定点 FFT,我能够从我采集的样本中获得 FFT 结果,但是当我对 FFT 结果进行 IFFT 时,我得到了错误的输出。

我正在做的程序流程如下

    对 8 个样本进行 FFT 举例说明:实数值为 (1,0,0,0,0,0,0,0),虚数值为 (0,0,0,0,0,0,0, 0) FFT 的输出为 (1,1,1,1,1,1,1,1),虚值为 (0,0,0,0,0,0,0,0) 然后取 FFT 输出的共轭 对共轭结果进行 FFT 再次取第二次 FFT 结果的共轭 最后除以8得到时域原始样本 输出是实数值是 (1,0,0,0,0,0,0,0) 虚数值是 (0,-0,-0,-0,-0,-0,-0,-0 );

但如果我对实数值 (1,2,3,4,5,6,7,8) 和虚数值 (0,0,0,0,0,0,0,0) 应用相同的值,我我得到错误的结果,例如IFFT之后的实数值是(1,2,4,7,4,5,4,5),虚数值是(-0,-3,-1,-0,1,0,0 ,2)

请帮助我做错了什么......

【问题讨论】:

你能显示每个步骤的示例值吗?您是否尝试过一个不是定点且不限于微控制器但遵循相同计算步骤的原型?可以发一下吗? 先生,我已经尝试过了,但我也没有得到...但是这个逻辑是为 IFFT 提到的 正如我在下面所说的,逻辑是(几乎)正确的,因为 IFFT(x)=conj(FFT(conj(x))/N,当输出时,第二个共轭应该无关紧要是真实的。因此,实现必须存在问题,只能在代码上进行分析,或者至少可以通过计算的痕迹来分析。 谢谢您的回复...我已经分析了代码FFT它的工作完美但是IFFT使用上面的逻辑它不是...这个逻辑是否正确?? 是的,逻辑是正确的。请测试输入序列 (1,0,0,...,0), (0,1,0,0,...,0),...,(0,0,0,..., 0,1) 并报告结果。输入和输出中复数的格式/排列/布局是否相同? 【参考方案1】:

FFT 解决插值问题,IFFT 解决相应的多点评估问题

FFT 的结果是多项式 p(z) 的系数,其中 p(wk)=xk,w 是与维度相关的单位根FFT 的 D。

用 ps,k(z) 表示由 p(z) 的系数的子序列形成的多项式,从 k 开始并以索引距离 s 间隔。

如果 D=2N 是偶数,从值到系数的一般思路是使用 wN=-1 和分解

p(z) = p2,0(z²) + z * p2,1(z²)

在关系中

xk = p(wk)=p2,0(w2k) + w k * p2,1(wk)

xN+k = p(wN+k) = p(-wk)

= p2,0(w2k) - wk * p2,1(w 2k)

将大插值问题减少为两个一半大小的子问题,

2*p2,0(w2k) = xk + xN+k

2*p2,1(w2k) = w-k * (xk - xN+k)

在下一步中,

p2,0 被缩减为 p4,0 和 p4,2,而 p2,1 减少到 p4,1 和 p4,3

等等。


对于 8 个输入的序列,第一步得到 w=(1+i)/sqrt(2) 和 w2=i

x1,0 = 2*p2,0( 1) = x0 + x4 x1,2 = 2*p2,0( i) = x1 + x5 x1,4 = 2*p2,0(-1) = x2 + x6子> x1,6 = 2*p2,0(-i) = x3 + x7子>

..

x1,1 = 2*p2,1( 1) = (x0 - x4子>)*1 x1,3 = 2*p2,1( i) = (x1 - x5 sub>)*(1-i)/sqrt(2) x1,5 = 2*p2,1(-1) = (x2 - x6)*(-i) x1,7 = 2*p2,1(-i) = (x3 - x7)*(-1-i)/sqrt(2)

在下一步中,得到 w=i 和 w2=-1

x2,0 = 4*p4,0( 1) = x1,0 + x1, 4 x2,4 = 4*p4,0(-1) = x1,2 + x1 ,6

..

x2,2 = 4*p4,2( 1)= (x1,0 - x1 ,4)*1 x2,6 = 4*p4,2(-1)= (x1,2 - x 1,6) * (-i)

--

x2,1 = 4*p4,1( 1) = x1,1 + x1, 5 x2,5 = 4*p4,1(-1) = x1,3 + x1 ,7

..

x2,3 = 4*p4,3( 1)= (x1,1 - x1 ,5)*1 x2,7 = 4*p4,3(-1)= (x1,3 - x 1,7) * (-i)

最后是 FFT 系数 Xk=x3,k 使用 w=-1 和 w²=1

X0 = 8*p8,0( 1) = x2,0 + x2,4 X4 = 8*p8,4( 1) = (x2,0 - x2,4 )*(-1)

--

X2 = 8*p8,2( 1) = x2,2 + x2,6 X6 = 8*p8,6( 1) = (x2,2 - x2,6 )*(-1)

--

X1 = 8*p8,1( 1) = x2,1 + x2,5 X5 = 8*p8,5( 1) = (x2,1 - x2,5 )*(-1)

--

X3 = 8*p8,3( 1) = x2,3 + x2,7 X7 = 8*p8,7( 1) = (x2,3 - x2,7 )*(-1)

请检查这些步骤是否反映在您的代码中,尤其是 2 的平方根是否出现在必要的位置。随机整数输入的输出不太可能再次是严格整数。

【讨论】:

【参考方案2】:

在您的描述中,您绝不会采用逆 DFT。

想想发生了什么,假设您的 DFT 结果为 X,取 X*X 将得到功率谱,而不是逆 DFT。然后对此进行 DFT 不会给你一个时域,它会给你废话。

您需要在您正在使用的库中找到逆 DFT 函数。

【讨论】:

您的评论总体上是正确的,但在 FFT 的情况下是错误的。你有 IFFT(x)=conj(FFT(conj(x))/N,所以原则上,这个算法应该可以工作。 你有那个来源吗?只看不匹配的傅里叶变换的积分形式。单位也不行。你有时间单位等于反时限 我们在这里处理 DFT,没有积分,只有和。单位不变。 DFT 是积分的特例,傅里叶变换确实会改变单位。您将某些东西从时间空间转移到频率空间,然后更改单位。 X[k]=sum(m=0 to N-1) exp(-2*piik*m/N)*x[m ] 单位会发生变化吗?

以上是关于通过对 FFT 结果进行共轭来使用 FFT 进行 IFFT的主要内容,如果未能解决你的问题,请参考以下文章

FFT仿真教程__Altera FFT

怎样用C语言实现FFT算法啊?

怎么利用FFT算法对音频噪声进行处理

使用 Apple Accelerate 框架选择实数和复数 2D FFT

在 fft 之后进行分类

时间对齐——用 FFT 加速互相关