rk3568上webrtc处理稳态噪声实践

前言:

大家好,在上一篇文章里面,我给大家介绍了webrtc里面的ns降噪处理流程,本篇文章,我给大家带来webrtc处理稳态噪声的一个测试,非稳态噪声,暂时没有测试,我们一步一步来,我先从最为基本的内容开始,后面再步入到算法原理细节,也就是webrtc里面的ns模块源码研究学习。

rk3568上测试webrtc降噪效果:

首先我这里是在rk3568上采集的wav音频数据:

这个可以不限制板子,我这里采集的命令如下:

go 复制代码
arecord -f S16_LE -r 16000 -c 1 clean.wav

下面是采集的噪声音频文件:

然后根据之前编译的降噪测试程序,进行降噪处理:

go 复制代码
./webrtc_ns_demo clean.wav out_clean.wav --ns moderate

也可以调整噪声的level:

go 复制代码
# 低(保真)
./webrtc_ns_demo clean.wav out_clean.wav --ns low

# 中(推荐)
./webrtc_ns_demo clean.wav out_clean.wav --ns moderate

# 高(抑噪最狠,可能吃音)
./webrtc_ns_demo clean.wav out_clean.wav --ns high

这里的降噪level是可以调整的,在AudioProcessing类成员里面有对level做描述:

go 复制代码
// Enables background noise suppression.抑制录音中的背景噪声(风声、空调声、键盘声、电流噪、机械噪声)
    /*
    WebRTC 的 NS 使用:
      频域(FFT-based)噪声估计
      谱减法(spectral subtraction)
      噪声估计更新
      维纳滤波(Wiener filter)
      语音优先增强(Speech-first gain)
    */
    struct NoiseSuppression {
      /*
      是否启用降噪。
        如果为 true,每一帧信号都会通过:
        FFT 分解成频谱
        估计噪声谱(noise power spectral density)
        做频域增益调整(Wiener gain)
        iFFT 重建时域信号
      */
      bool enabled = false;
      /*
        降噪等级。
        | Level           | 噪声抑制力度   | 人声保真度           |
        | --------------- | --------    | --------------- |
        | `kLow`          | 轻度降噪     | 保真最高            |
        | `kModerate`(默认) | 中等降噪     | 保真 + 降噪均衡       |
        | `kHigh`         | 强降噪      | 人声略受影响,降低背景噪更明显 |
        | `kVeryHigh`     | **暴力降噪** | 人声可能干,但背景噪能大幅下降 |

        实际效果:
            kLow:轻微降噪
            kModerate:正常通话(会议场景最佳)
            kHigh:嘈杂环境(机器声、风声)
            kVeryHigh:强噪场景(工厂机器、风声、飞机噪音等)
      */
      enum Level { kLow, kModerate, kHigh, kVeryHigh };
      Level level = kModerate;
      /*
      如果 AEC 可用,那么 NS 的噪声分析会基于 linear AEC 输出
    (提高噪声估计精度)
      */
      bool analyze_linear_aec_output_when_available = false;
    } noise_suppression;

    // TODO(bugs.webrtc.org/357281131): Deprecated. Stop using and remove.
    // Enables transient suppression.
    /*
    什么是 Transient Suppression(瞬态噪声抑制)?
    Transient = "瞬态噪声"指:
        键盘敲击声
        鼠标点击声
        门开关咔哒声
        盘子碰撞叮当声
        桌子敲击声
        一些突发的高幅度、短时噪声
    Transient 噪声特点:
      持续时间极短(几毫秒)
      幅度通常比背景噪声大
      频率成分不稳定
      不像风噪那样连续,也不像语音那样稳定
      这种噪声对语音影响巨大:
      听感刺耳
      使降噪算法难以正确工作
      NLP/AEC 会误判
      波形破坏大
      Transient Suppression 模块的目标:
      识别突发瞬态噪声并对其做抑制,避免爆音或刺耳瞬间噪声。
    */
    struct TransientSuppression {
      bool enabled = false;
    } transient_suppression;

我这里是使用kModerate测试的效果,降噪后的音频文件如下:

大家可以在看文章的时候听一下两个音频前后的效果,处理效果还是不错的。

下面我们打开这两个文件的频谱图看一下:

第一个带噪声的音频频谱图


处理后的音频频谱图

webrtc的降噪源码入口:

这里我们暂时不会讲解源码,这里只是为后续讲解做铺垫,首先这里要学习降噪的算法原理细节,肯定是要看源码的,所以整个处理入口要找到类似下面的处理

go 复制代码
PCM
 ↓
STFT(短时傅里叶变换)
 ↓
噪声谱估计(基于非语音帧)
 ↓
Wiener-like 频域增益计算
 ↓
时间/频率平滑
 ↓
逆 STFT

Ok,我们从webrtc的demo开始:

  • 1、找到apm->ProcessStream接口
  • 2、找到ProcessCaptureStreamLocked接口:
  • 3、找到处理噪声接口submodules_.noise_suppressor->Process(capture_buffer);

上面的Process就是webrtc降噪算法最为核心的内容:

go 复制代码
void NoiseSuppressor::Process(AudioBuffer* audio)

总结:

从今天的文章开始,我们就正式打通了webrtc音频降噪功能了,有实操有理论,完美,当然后面的内容还有很多,我尽量把自己理解到的内容分享出来,我们下期见,准确来说,应该是明年见了,哈哈!

相关推荐
做科研的周师兄1 小时前
【MATLAB 实战】栅格数据 K-Means 聚类(分块处理版)—— 解决大数据内存溢出、运行卡顿问题
人工智能·算法·机器学习·matlab·kmeans·聚类
X在敲AI代码1 小时前
leetcodeD3
数据结构·算法
码农小韩1 小时前
基于Linux的C++学习——循环
linux·c语言·开发语言·c++·算法
CoderCodingNo1 小时前
【GESP】C++五级/四级练习(双指针/数学) luogu-P1147 连续自然数和
开发语言·c++·算法
颜酱1 小时前
前端算法必备:双指针从入门到很熟练(快慢指针+相向指针+滑动窗口)
前端·后端·算法
Wect1 小时前
LeetCode 274. H 指数:两种高效解法全解析
算法·typescript
Q741_1471 小时前
海致星图招聘 数据库内核研发实习生 一轮笔试 总结复盘(2) 作答语言:C/C++ 哈夫曼编码 LRU
c语言·数据库·c++·算法·笔试·哈夫曼编码·哈夫曼树
Hello.Reader1 小时前
PyFlink DataStream Operators 算子分类、函数写法、类型系统、链路优化(Chaining)与工程化踩坑
前端·python·算法
hweiyu001 小时前
最短路径算法:Floyd-Warshall算法
算法
荒诞硬汉1 小时前
数组常见算法
java·数据结构·算法