使用核心音频实现后处理低通滤波器

Posted

技术标签:

【中文标题】使用核心音频实现后处理低通滤波器【英文标题】:Implementing a post-processed low-pass filter using core audio 【发布时间】:2010-11-12 07:33:14 【问题描述】:

我已经使用基于时间的值实现了一个基本的低通滤波器。这没关系,但试图找到正确的时间片是猜测工作,并根据不同的输入音频文件给出不同的结果。这是我现在拥有的:

- (void)processDataWithInBuffer:(const int16_t *)buffer outBuffer:(int16_t *)outBuffer sampleCount:(int)len    
    BOOL positive;
    for(int i = 0; i < len; i++) 
        positive = (buffer[i] >= 0);
        currentFilteredValueOfSampleAmplitude = LOWPASSFILTERTIMESLICE * (float)abs(buffer[i]) + (1.0 - LOWPASSFILTERTIMESLICE) * previousFilteredValueOfSampleAmplitude;
        previousFilteredValueOfSampleAmplitude = currentFilteredValueOfSampleAmplitude; 
        outBuffer[i] = currentFilteredValueOfSampleAmplitude * (positive ? 1 : -1);
    

如何将此代码转换为允许我将某个 hz 上的频率降低某个 db 级别的代码?

【问题讨论】:

【参考方案1】:

我强烈推荐numerical recipes in c。除此之外,我不确定我能帮助你。

当您设计一个滤波器时,您需要根据频率计算该滤波器的系数,因此您几乎需要一个类来处理它,而不仅仅是一个函数。

这是在C++ 但它应该让你开始。抱歉,我无法提供具体答案。

【讨论】:

这个函数是执行缓冲和文件工作的类的核心。一切正常,但我想转换为 hz 和 db,而不是使用基于时间的切片作为唯一的 var 啊,好的。查看我在C++ 下链接到的代码,这实际上非常好。它会根据频率返回一个过滤器。 正是我想要的。很棒的发现 @coneybeare,很高兴我能帮上忙。【参考方案2】:

您拥有的是 IIR 滤波器,为了获得更多控制,我建议使用 FIR 滤波器,它更容易计算系数。我创建了一个窗口函数:

y = sin (x * bandwidth) / (sin (x) * windowWidth)

windowWidth 是窗口宽度的样本数,x 范围从 -2 * PI 到 2 * PI,以及带宽:

bandwidth = 2 * frequency * n / sampleRate;

这会创建一个数字数组,您可以将这些数字应用于以您要输出的样本为中心的一系列样本。您对每个样本进行迭代。

我已经总结了我自己的代码,因为原始代码相当粗糙。

【讨论】:

windowWidth 是缓冲区数组的长度?还是更小的东西?我最终选择了 Stephen Furlani 链接的巴特沃斯低通滤波器,它似乎工作得很好,所以如果我有额外的时间,我会试试你的 windowWidth 从 3 开始可变。上限是基于你愿意代码的慢速。更大的窗口会导致更陡峭的截止。一般来说,您不需要超过 63。此外,奇数值效果最好。 很好的答案。我已经忘记了我的大部分信号处理......并发布了糟糕的代码。 :D【参考方案3】:

我使用interactive filter designer 实现了一个过滤器。

这里有一些示例代码,集成了它:https://github.com/davidcairns/MediaPlayerDemo

【讨论】:

以上是关于使用核心音频实现后处理低通滤波器的主要内容,如果未能解决你的问题,请参考以下文章

什么是高通和低通滤波器?

低通滤波器的设计和计算

NAudio 低通滤波器

如何使用 fft 为音频创建低通滤波器

语音处理基于matlab音频信号FIR+IIR(高通+低通+带通)滤波器频谱分析含Matlab源码 1732期

用MATLAB设计对信号进行频谱分析和滤波处理的程序