2015-09-07 1 views
0

Мне почти что это нужно задокументировать, но я не мог найти. Поэтому я предполагаю, что, возможно, неправильно понимаю API kissFFT.Как правильно использовать kissFFT с C++-вектором?

Я просто хочу использовать kissFFT в проекте C++ с помощью stl :: vector, чтобы легко обрабатывать сигнал произвольной длины. Для этого я отредактировал this SO answer от автора kissFFT. Я заменил

std::complex<float> x[nfft]; с

vector<std::complex<float>> x(nfft, 0.0);

и заменить вызов функции

kiss_fft(fwd,(kiss_fft_cpx*)x,(kiss_fft_cpx*)fx) с

kiss_fft(fwd,(kiss_fft_cpx*)&x[0],(kiss_fft_cpx*)&fx[0]);

Это, кажется, работает довольно хорошо, но это право способ сделать это? В папке «test» kissFFT, если найдена «testcpp.cc», которая, похоже, использует некоторые причудливые возможности C++-шаблона - к сожалению, для меня. Я не мог скомпилировать его. Имеет ли мое решение какие-либо недостатки?


Это - полный код. Может быть, это поможет другим:

#include "kiss_fft.h" 
#include <complex> 
#include <iostream> 
#include <vector> 
using namespace std; 

int main() 
{ 
    const int nfft=256; 
    kiss_fft_cfg fwd = kiss_fft_alloc(nfft,0,NULL,NULL); 
    kiss_fft_cfg inv = kiss_fft_alloc(nfft,1,NULL,NULL); 

    vector<std::complex<float>> x(nfft, 0.0); 
    vector<std::complex<float>> fx(nfft, 0.0); 

    x[0] = 1; 
    x[1] = std::complex<float>(0,3); 

    kiss_fft(fwd,(kiss_fft_cpx*)&x[0],(kiss_fft_cpx*)&fx[0]); 
    for (int k=0;k<nfft;++k) { 
     fx[k] = fx[k] * conj(fx[k]); 
     fx[k] *= 1./nfft; 
    } 
    kiss_fft(inv,(kiss_fft_cpx*)&fx[0],(kiss_fft_cpx*)&x[0]); 
    cout << "the circular correlation of [1, 3i, 0 0 ....] with itself = "; 
    cout 
     << x[0] << "," 
     << x[1] << "," 
     << x[2] << "," 
     << x[3] << " ... " << endl; 
    kiss_fft_free(fwd); 
    kiss_fft_free(inv); 
    return 0; 
} 

ответ

1

Я предпочитаю использовать std::vector<kiss_fft_cpx> себя, но в остальном мой код почти так же, как ваша. (Ну, kiss_fft_alloc и kiss_fft_free идут в CTOR/dtor, чтобы избежать утечек памяти, но это стиль вещь.)

Чуть дальше вниз, fx[k] * conj(fx[k]) является типичным математическим выражением. Эффективно использовать fx[k].norm().

+0

спасибо. Но первый отрывок вашего ответа я действительно не понял. Я пытаюсь объяснить, что я получил до сих пор: kissFFT expexts вектор kiss_fft_cpx, но в моем примере он получает вектор std :: complex. Это может привести к утечке памяти, но поскольку 'kiss_fft_alloc' и' kiss_fft_free' вызывает конструктор/деструктор чего-то (std :: complex ???), на практике не будет проблем. –

+0

Другой вопрос: fwd и inv сохранить конфигурацию. Если я использую одну конфигурацию, второй раз будет быстрее, как в первый раз (потому что коэффициенты twiddle или что-то подобное уже рассчитаны)? –

+0

@Ergodicity: Вероятно, вы получите быстрый ответ, просто попробовав. – MSalters