简单的音频滤波器组

6

我对音频滤波不熟悉,如果我说错了什么,请见谅。

我想编写一段代码,可以将存储在PCM样本中的音频分成两个或三个频带,并对它们进行一些操作(如修改其音频级别)或分析,然后从输出中重构音频样本。

据我在互联网上阅读的资料,我可以使用FFT-IFFT并对复杂形式进行操作,或者使用基于时间域的滤波器组,例如MP2音频编码格式所使用的。也许滤波器组是更好的选择,至少我在某个地方读到过,在实时流环境中可能更加CPU使用友好。然而,我很难理解滤波器组背后的数学知识。我正在尝试找到一些关于此主题的源代码(最好是Java或C / C ++),但迄今为止没有成功。

有人能提供一些提示或链接,让我更接近一个示例滤波器组吗?


FFT-操作-IFFT 可能是最容易实现和最灵活的。 - Paul R
http://staffwww.dcs.shef.ac.uk/people/N.Ma/resources/gammatone/ - some_id
你找到了特定的过滤器吗?我想尝试在我的项目中使用小波滤波器组,但是好像小波与常规滤波器不太相似。例如,你可以输入数据流并输出过滤后的数据流,而使用小波时,我不知道它们是否主要设计用于数据流的输入输出?你有解决方案吗? - bandybabboon
3个回答

8
使用FFT将音频信号分成几个频段是过度的。你需要的是一个或两个Linkwitz-Riley滤波器。这些滤波器将信号分成高频和低频部分。
这种滤波器的一个好处是,如果你将低频和高频部分相加,你几乎可以得到原始信号。会有一点相位移动,但耳朵听不出来。
如果你需要更多的频段,可以串联这些滤波器。例如,如果你想在100Hz和2000Hz处分离信号,伪代码如下:
low  = linkwitz-riley-low (100, input-samples)
temp = linkwitz-riley-high (100, input-samples)

mids = linkwitz-riley-low (2000, temp)
highs = linkwitz-riley-high (2000, temp);

分离信号后,您可以放大三个输出频段:低音、中音和高音,然后将它们相加以获得处理后的信号。
滤波器部分本身可以使用IIR滤波器实现。搜索“Linkwitz-Riley数字IIR”应该会得到很多好的结果。 http://en.wikipedia.org/wiki/Linkwitz-Riley_filter

这正是我正在寻找的东西。现在我只需要找到一个例子就好了 :) - NagyI
1
我刚刚在Java中实现了来自此代码的滤波器(评论中的二阶版本)。它运行良好。但是,截止频率不如我预期的那么锐利。我该如何改进呢?使用四阶版本会更好吗? - NagyI

5

你应该了解小波变换,特别是道贝西小波。它们可以帮助你完成这个技巧,它们是FIR滤波器,并且非常短。

更新 没有解释就给负评是不好的行为。另外,我是正确的。小波变换是滤波器组,它们的工作就是如问题所述的那样。在我看来,是这样的。我自己也做过很多次。


这看起来很有趣,谢谢提及。我已经找到了一篇关于音频和小波的好论文在这里。然而,完全理解它仍然超出了我的能力范围,我也找不到示例程序的源代码。 - NagyI
@Phonon,如果你愿意分享一些简单的示例代码,我很想看看。+1 - learnvst
@learnvst 我需要找到我的旧笔记本电脑,所以给我一两天时间。我有一些 MATLAB 例程可以做这个。 - Phonon
@Phonon 听起来很棒。我会耐心等待。 - learnvst

3

这里可以找到很多滤波器源代码,点击此处查看。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接