为啥我的 NAudio FFT 结果与 MATLAB 相差 4 倍?
Posted
技术标签:
【中文标题】为啥我的 NAudio FFT 结果与 MATLAB 相差 4 倍?【英文标题】:Why does my NAudio FFT result differ from MATLAB by a factor of 4?为什么我的 NAudio FFT 结果与 MATLAB 相差 4 倍? 【发布时间】:2018-06-11 21:15:38 【问题描述】:以下 C# NAudio 代码与 MATLAB 产生的结果相差 4 倍。为什么会发生这种情况,其中一个是不正确的?
Complex[] tmp = new Complex[4];
tmp[0].X = 1.0f;
tmp[1].X = 0.5f;
tmp[2].X = 1.0f;
tmp[3].X = 0.25f;
tmp[0].Y = 0.0f;
tmp[1].Y = 0.0f;
tmp[2].Y = 0.0f;
tmp[3].Y = 0.0f;
FastFourierTransform.FFT(true, 2, tmp);
音频输出:
0.6875 + 0.0000i
0.0000 - 0.0625i
0.3125 + 0.0000i
0.0000 + 0.0625i
MATLAB 输出:
2.7500 + 0.0000i
0.0000 - 0.2500i
1.2500 + 0.0000i
0.0000 + 0.2500i
【问题讨论】:
我相信 matlab 的实现。要找到问题,也许您可以使用具有特定频率的较长信号,然后观察频谱。 【参考方案1】:Discrete Fourier transform 及其逆需要一定的归一化,以便ifft(fft(x))==x
。这种规范化的完成方式因实施而异。
在这种情况下,NAudio 似乎选择了与 MATLAB 不同的标准化。
MATLAB 使用最常见的归一化,其中k=0
处的fft(x)
等于sum(x)
,逆变换做同样的事情,但除以n
(样本数)。这也是Wikipedia page for the DFT 中描述的等式。在这种情况下,逆变换匹配傅里叶级数的方程。
NAudio 似乎在前向变换中通过n
进行除法,因此在k=0
你有mean(x)
。
鉴于上述情况,您可以使用第一个频率区间(直流分量)来验证使用了什么归一化(假设有直流分量,如果信号为零意味着这将不起作用):如果直流分量等于所有样本值的总和,则使用“通用”归一化。在对称定义的情况下,它也可以等于总和除以sqrt(n)
,其中正向和逆变换进行相同的归一化。对于 NAudio,它将等于总和除以 n
(即样本值的平均值)。通常,取直流分量并除以样本值的总和。结果q
是使用的规范化术语。逆变换应该有一个归一化项1/qn
。
【讨论】:
我认为这意味着两者都不正确,除非您确定某种电平校准,否则将 am 幅度图的绝对能量/功率与 2 种不同 FFT 算法计算的绝对能量/功率进行比较总是不明智的已经发生。这意味着我可以继续使用 NAudio,而无需对复杂的数据进行任何手动更正。 @AlexS:FFT 不计算能量或功率,它计算 DFT。只要您知道 FFT 算法使用的 DFT 的定义,您就可以从那里轻松计算能量/功率。请注意,只需查看频率 0 的输出,您就可以找出正在使用的归一化。 -- 我的意思是,在将单位添加到任何绘图之前,您需要知道您计算的内容... :) 谢谢,在这种情况下,您能否详细说明如何使用第一个频率箱 0 Hz(或 DC)确认归一化方法,我认为这将证明它们是相同的,并且答案将是完整的。 @Alex:我添加了一段关于如何检查规范化的内容。这是你的想法吗?以上是关于为啥我的 NAudio FFT 结果与 MATLAB 相差 4 倍?的主要内容,如果未能解决你的问题,请参考以下文章
为啥不使用 Scipy 的 FFT 代码中的结果与 Scipy FFT 不相似?
序列的离散傅里叶变换(DFT)的来龙去脉并附利用MATLA的函数FFT()求序列的DFT的示例