快速和慢速时间加权对实时音频信号处理意味着什么?

信息处理 matlab 声音的 声音
2022-02-20 04:48:43

我有一个正在实时录制的流式音频信号。为了便于解释,假设我收到的信号经过校准并具有采样频率,Fs=44100 Hz.

然后我找到了这个信号的声压级。为此,我得到了一帧 t 秒的音频数据。

然后,RMS 声压级 (dB) 由下式给出:

AmplitudeRMS=mean(frame2)

这给出了一个瞬时 RMSt-第二帧音频。然后,找一个 dB等级,

Lp=20log10(AmplitudeRMS)

对于“快”或“慢”声压级的定义,这里的事情变得很棘手。正如这篇文章所指出的,对于时间加权指数平均,我创建了一个低通滤波器,其实极点位于1/τ(在哪里τ=125 ms对于“快速”或1 s对于“慢”)

τ = 0.125; %fast
[b a] = bilinear(1, [1 1/τ], Fs);
frame_filtered = filter(b, a, frame.^2);
L_fast = 20*log10(sqrt(mean(frame_filtered)));

IEC 61672 将时间权重指定为快速和慢速,以确定仪器对不断变化的噪声水平的响应速度

  • 这对数字音频有何作用?
  • 这是否意味着需要对固定的数据框架进行分析?
  • 对于这个特定的例子,这个框架将是tFs样品?

    慢:1*44100 = 441000 个样本
    快速:0.125*44100 ~= 5513 个样本

  • 如果是这样,我是否需要提前知道我需要快速还是慢速关卡?

1个回答

通过声学中的“时间加权”,我们将 RC(电阻-电容)电路应用于时间信号。

参见:维基百科上的RC 电路

FAST 的时间常数为 0,125 s,SLOW 的时间常数为 1 s。

您也可以使用下面的代码以数字方式将其应用于您的时间信号 - 它基本上是一个指数移动平均滤波器我认为您只需查看下面代码中的注释即可理解这些步骤。

公共类 FilterTimeWeighting {

private int nBands = 29; //number of bands
private float initValue;

FilterTimeWeighting() {
    initValue=0;
}

/**
 * Apply the LAmax RC-filter on the signal. Valid for fsamp=44100 Hz.
 * Returns the signal in Volts after applying filter.
 * 
 * //y(n)=a*y(n-1)+(1-a)*x(n)
 *
 * 
 *
 * @param signalIn
 * @return
 */
public float[] applyLmaxFilter(float[] signal) {

    int n_samples = signal.length;

    float[] x_signal = new float[n_samples];
    float[] y_signal = new float[n_samples];
    float[] ret_signal = new float[n_samples];


    //Square the signal
    for (int i_sample = 0; i_sample < n_samples; i_sample++) {
        x_signal[i_sample] = signal[i_sample] * signal[i_sample];
    }

    //Exponential moving average parameters
    float tau=0.125f;
    float fs=44100f;
    float alpha=tau/(1f/fs+tau);

    //for the first sample 
    y_signal[0] = initValue*alpha+(1-alpha)*x_signal[0];

    //for the rest of the samples
    for (int i_sample = 1; i_sample < n_samples; i_sample++) {
        y_signal[i_sample] = y_signal[i_sample-1]*alpha+(1-alpha)*x_signal[i_sample];
    }

    //remember last sample for next time step;
    initValue=y_signal[n_samples-1];

    //Square root
    for (int i_sample = 0; i_sample < n_samples; i_sample++) {
        ret_signal[i_sample] = (float) Math.sqrt(y_signal[i_sample]);
    } 

    return ret_signal;
}

}