简体   繁体   English

kissfft-逆实数FFT给出NaN

[英]kissfft - Inverse Real FFT gives NaN

The real inverse FFT gives me an array full of NaN s instead of floats . 真正的逆FFT给了我一个充满NaN而不是浮点数的数组。

kiss_fftri(conf,complex_array,output);

The complex_array is normal, nothing wrong with the values i guess. complex_array是正常的,我猜的值没有问题。

kiss_fftr_cfg conf = kiss_fftr_alloc(size,1,NULL,NULL);

The conf should be fine too as far as I know. 就我所知, conf应该也可以。

Anything wrong with the size ? 大小有问题吗? I know that the output size of the forward FFT must be N/2 + 1 and the size above should be N . 我知道前向 FFT的输出大小必须为N / 2 +1 ,而上面的大小应为N。

I've already made an simple working example with audio convolution in the frequency domain and everything, but I've no idea whats happening here . 我已经通过频域和所有方面的音频卷积制作了一个简单的工作示例, 但是我不知道 这里 发生 什么


在此处输入图片说明在此处输入图片说明

NaNs and some samples of the , complex_array above. NaN和上面的complex_array的一些示例。

The size parameter in my example is always 18750 . 在我的示例中, size参数始终为18750 Thats the number of samples. 多数民众赞成在样本数量。 N / 2 + 1 is therefore 7876 . 因此,N / 2 + 1是7876

First I'm having a mono channel with 450k samples. 首先,我有一个带有450k样本的单声道。 Then I'm splitting it on 24 parts. 然后将其分为24个部分。 Every part is now 18750 samples. 现在每个部分都是18750个样本。 With each of those samples I'm making an convolution with an impulse response. 对于每个样本,我都在用脉冲响应进行卷积。 So basically the numbers I'm printing above are lets say the first 20 samples in each of the 24 rounds the for loop is going. 所以基本上我在上面打印的数字可以说是for循环进行的每24回合中的前20个样本。 Nothing wrong here I guess. 我猜这里没错。

I even did on kiss_fftr_next_fast_size_real(size) and it stays the same so the size should be optimal. 我什至对kiss_fftr_next_fast_size_real(size)进行了处理,并且它保持不变,因此大小应该是最佳的。


Here's my convolution: 这是我的卷积:

kiss_fft_cpx convolution(kiss_fft_cpx *a, kiss_fft_cpx *b, int size)
{
    kiss_fft_cpx r[size];
    memset(r,0,size*sizeof(kiss_fft_cpx));
    int skalar = size * 2; // for the normalisation
    for (int i = 0; i < size; ++i){
        r[i].r = ((a[i].r/skalar) * (b[i].r)/skalar) - ((a[i].i/skalar) * (b[i].i)/skalar);
        r[i].i = ((a[i].r/skalar) * (b[i].i)/skalar) + ((a[i].i/skalar) * (b[i].r)/skalar);
    }
    return r;
}

The size I input here via the argument is the N/2 + 1 . 我在这里通过参数输入的大小N / 2 +1

It's not kiss which causes the problem here. 不是接吻会在这里引起问题。 It is how the result array is (mis)handled. 结果数组被(错误)处理。

To really "keep it simple and stupid" (KISS), I recommend to use STL containers for your data instead of raw c++ arrays. 为了真正做到“简单而愚蠢”(KISS),我建议对数据使用STL容器,而不要使用原始c ++数组。 This way, you can avoid the mistakes you did in the code. 这样,您可以避免在代码中犯的错误。 Namely returning the array you created on the stack. 即返回您在堆栈上创建的数组。

kiss_fft_cpx convolution(kiss_fft_cpx *a, kiss_fft_cpx *b, int size)

... bears various problems. ……有各种各样的问题。 The return type is just a complex number, not a series. 返回类型只是一个复数,而不是一个序列。

I would change the signature of the function to: 我将函数的签名更改为:

#include <vector>
typedef std::vector<kiss_fft_cpx> complex_vector;
void 
convolution
( const kiss_fft_cpxy *a
, const kiss_Fft_cpx *b
, int size
, complex_vector& result 
);

Then, in the code, you can indeed resize the result vector to the necessary size and use it just like a fixed size array as far as your convolution computation is concerned. 然后,在代码中,实际上可以将结果向量调整为必要的大小,并就卷积计算而言就像固定大小的数组一样使用它。

{
    result.resize(size);
    // ... use as you did in your code: result[i] etc..
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM