如何从fft获得频率结果?
我在我的Android手机上录制了来自我的麦克风的数据[1024],并通过实际数据的一维正向DFT(将另外的1024位设置为0)传递给它。 我将这个数组保存到一个文本文件中,并重复这8次。
我回来了16384的结果。 我打开Excel中的文本文件,并创build一个graphics,看看它是什么样子(x =数组的索引,y =返回的数字的大小)。 有一些大规模的尖峰(包括积极的和消极的),数量在110,232左右,而小尖峰一直延续到1817年和1941年,尖峰再次变大,然后再次下降。
我的问题是,无论我在哪里寻找帮助的话题,都提到gettng的实数和虚数,我只有一维数组,我从我从Piotr Wendykier的类使用的方法回来:
DoubleFFT_1D.realForwardFull(audioDataArray); // from the library JTransforms.
我的问题是:我需要做什么来这个数据返回一个频率? 录制的声音是我在我的吉他的底弦(第五品)上(大约440Hz)播放“A”。
复数据是交错的,偶数的实数分量和奇数的虚数分量,即实数分量在索引2*i
,虚数分量在索引2*i+1
。
为了得到指数i的频谱大小,你需要:
re = fft[2*i]; im = fft[2*i+1]; magnitude[i] = sqrt(re*re+im*im);
然后你可以绘制幅度[我]为i = 0到N / 2来获得功率谱。 根据audioinput的性质,您应该在频谱中看到一个或多个峰值。
要获得任何给定峰的近似频率,您可以按如下方式转换峰的指数:
freq = i * Fs / N;
哪里:
freq = frequency in Hz i = index of peak Fs = sample rate (eg 44100 Hz or whatever you are using) N = size of FFT (eg 1024 in your case)
注意:如果您以前没有对时域input数据应用合适的窗口函数 ,那么您将得到一定的频谱泄漏 ,功率谱看起来相当“模糊”。
为了进一步扩展,下面是一个完整的例子的伪代码,我们可以获取audio数据并确定最大峰值的频率:
N = 1024 // size of FFT and sample window Fs = 44100 // sample rate = 44.1 kHz data[N] // input PCM data buffer fft[N * 2] // FFT complex buffer (interleaved real/imag) magnitude[N / 2] // power spectrum capture audio in data[] buffer apply window function to data[] // copy real input data to complex FFT buffer for i = 0 to N - 1 fft[2*i] = data[i] fft[2*i+1] = 0 perform in-place complex-to-complex FFT on fft[] buffer // calculate power spectrum (magnitude) values from fft[] for i = 0 to N / 2 - 1 re = fft[2*i] im = fft[2*i+1] magnitude[i] = sqrt(re*re+im*im) // find largest peak in power spectrum max_magnitude = -INF max_index = -1 for i = 0 to N / 2 - 1 if magnitude[i] > max_magnitude max_magnitude = magnitude[i] max_index = i // convert index of largest peak to frequency freq = max_index * Fs / N