9

我正在用 Java 实现 MFCC 算法。

这里有一个示例代码:http ://www.ee.columbia.edu/~dpwe/muscontent/practical/mfcc.m at Matlab。但是,我在 mel 过滤器存储过程中遇到了一些问题。如何生成三角形窗口以及如何使用它们?

PS1:一篇文章,其中有描述 MFCC 的部分:http: //arxiv.org/pdf/1003.4083

PS2:如果基本有MFCC算法步骤的文档就好了。

PS3: 我的主要问题与此有关:MFCC with Java Linear and Logarithmic Filters一些实现同时使用线性和对数滤波器,而其中一些不使用。什么是过滤器和什么是中心频繁的概念。我遵循该代码:MFCC Java,该代码之间有什么区别:MFCC Matlab

4

2 回答 2

4

作为频带滤波器的三角窗并不难实现。您基本上希望在每个频段内集成 FFT 数据(定义为中心频率i-1和中心频率之间的频率空间i+1)。

你基本上是在寻找类似的东西,

for(int bandIdx = 0; bandIdx < numBands; bandIdx++) {
    int startFreqIdx  = centerFreqs[bandIdx-1];
    int centerFreqIdx = centerFreqs[bandIdx];
    int stopFreqIdx   = centerFreqs[bandIdx+1];

    for(int freq = startFreqIdx; i < centerFreqIdx; i++) {
        magnitudeScale = centerFreqIdx-startFreqIdx;
        bandData[bandIdx] += fftData[freq]*(i-startFreqIdx)/magnitudeScale;
    }

    for(int freq = centerFreqIdx; i <= stopFreqIdx; i++) {
        magnitudeScale = centerFreqIdx-stopFreqIdx;
        bandData[bandIdx] += fftData[freq]*(i-stopFreqIdx)/magnitudeScale;
    }
}

如果您不了解“中心频率”或“频带”或“滤波器”的概念,请拿起一本基本信号教科书——您不应该在不了解它的作用的情况下实现该算法。

至于确切的中心频率是多少,这取决于您。试验并挑选(或在出版物中查找)捕获您希望从数据中分离出来的信息的值。之所以没有确定的值,甚至是值的尺度,是因为该算法试图逼近人耳,这是一种非常复杂的听音设备。一种音阶可能更适合演讲,而另一种音阶可能更适合音乐等。您可以选择合适的音阶。

于 2011-06-03T23:27:32.850 回答
3

回答第二个 PS:我发现这个教程真的帮助我计算了 MFCC。

至于三角形窗口和滤波器组,据我了解,它们确实重叠,它们不会扩展到负频率,并且从 FFT 频谱计算它们并将它们应用回它的整个过程如下所示:

  1. 为滤波器选择最小和最大频率(例如,最小频率 = 300Hz - 最小语音频率和最大频率 = 您的采样率 / 2。也许这就是您应该选择您所说的 1000Hz 限制的地方)
  2. 根据选择的最小和最大频率计算 mel 值。公式在这里
  3. 计算这两个 mel 值之间的 N 个等距值。(我已经看到 N 的不同值的示例,您甚至可以在这项工作中找到不同值的效率比较,对于我的测试,我选择了 26)
  4. 将这些值转换回 Hz。(您可以在同一个 wiki 页面上找到公式)=> N + 2 个过滤器值的数组
  5. 为每三个连续值计算一个过滤器组(过滤器三角形),无论是 Thomas 上面建议的方式(注意索引)还是本文开头推荐的教程)=> 一个数组数组,大小为 NxM,假设你FFT 返回 2*M 值,您只使用 M。
  6. 将整个功率谱(从 FFT 获得的 M 值)通过每个三角滤波器,以获得每个滤波器的“滤波器组能量”(对于每个滤波器组(N 个循环),将 FFT 后获得的每个幅度乘以相应滤波器组中的每个值(M循环)并添加 M 获得的值)=> N 大小的能量数组。

这些是您的滤波器组能量,您可以进一步应用对数、应用 DCT 并提取 MFCC……

于 2013-03-22T15:05:43.707 回答