我试图通过使用FFTW库的函数对C 中的两个信号 和进行卷积,对每个信号执行傅里叶变换,将适当的复杂分量相乘,然后对结果乘积进行 IFFT。不幸的是,我的 IFFT 结果不正确,我不确定我做错了什么。
我正在使用我在网上找到的代码的修改版本(此处为 .c 和 Makefile )进行测试,该版本使用 0 到 1 之间的随机数填充两个数组。我的过程如下:
- 分别为长度和长度的(音频信号)和(脉冲响应)创建
double
缓冲区。x
h
n
nIR
- 用 0 到 1 之间的随机数填充每个缓冲区。
- 创建两个
complex
缓冲区X
和H
,每个缓冲区的长度nOut = n + nIR - 1
- 创建并执行两个从实数到复数的 FFT 计划,每个信号一个,都使用
nOut
元素(即plan_forward = fftw_plan_dft_r2c_1d ( nOut, x, X, FFTW_ESTIMATE );
和plan_forwardIR = fftw_plan_dft_r2c_1d (nOut, h, H, FFTW_ESTIMATE);
- 创建复数数组
fftMulti
以保存两个数组的频率乘积。它的大小是nc = nOut / 2 + 1
因为 FFTW 不存储 FFT 的冗余一半 - 循环
for ( i = 0; i < nc; i++ )
并执行复数乘法,即fftMulti[i][0] = X[i][0] * H[i][0] - X[i][1] * H[i][1];
实部和fftMulti[i][1] = X[i][0] * H[i][1] + X[i][1] * H[i][0];
虚部 - 创建大小
double
数组。该数组将保存 IFFTconvolvedSig
nOut
fftMulti
- 创建并执行大小为 的复数到实数的 FFT 计划
nOut
,即plan_backwardConv = fftw_plan_dft_c2r_1d(nOut, fftMulti, convolvedSig, FFTW_ESTIMATE);
convolvedSig
通过将每个元素除以标准化nOut
中的值convolvedSig
不正确(它们太高了),但我不确定我做错了什么。我还为我未修改的信号X
和H
(也是大小nOut
)创建了数组和复数到实数的计划,并且这些 IFFT 工作得很好(即,值与我对它们执行 FFT 之前的值完全相同)。
使用我的流程和/或我的代码,有人可以帮我确定我做错了什么吗?