即时通讯开发之如何测试实时语音通话质量

news2025/2/24 8:49:59

实时语音聊天开发,对于一般的开发者来说比较神秘,很多朋友不太清楚如何全面的评估一个音频引擎。很多朋友还停留在这样的初级阶段:把demo调通,找几个人喂喂喂......凭自己优异的听觉感受一下,整个测试过程就完成了。

 

但是,少年!如果就这么简单,你很有可能遇到下面的这些坑:

    我们花了好多钱买了一套基于硬件的解决方案,开始用的还行,怎么现在越来越卡了?
    我们评估了某个引擎,自己内网测试的时候感觉声音很流畅,延时很小。为什么上线了很多用户说又卡又延时啊?
    我们用WebRTC做了一套方案,iPhone上还好,但是为什么在安卓的机器上老是有回声啊?
    为什么我昨天用的还好好的,今天换了个手机/地方/网络打效果差好多啊?


如何科学的测试语音通话质量,这是本文提纲:

    首先,普及一下,哪些因素会影响对音频质量的评估。
    然后,我们再来看需要做哪些测试。
    最后,我们讨论一下大家比较关心的WebRTC框架中的音频模块如何,是否适合商用?

网络对音频质量的影响是非常直观的,如果承载音频信息的语音包在网络传输的过程中丢失,晚到,或者不均匀的到,就会造成我们常说的丢包,延时和抖动。

从主观听感上造成声音的卡顿和滞后,严重影响通话的质量和可懂度。在公共互联网上,特别是在远距离通信的情况下,如果缺乏足够的网络部署和音频的丢包对抗技术,这种情况就会变得尤为明显。如果是在内网环境,两人通话的场景下,声音可以通过点对点(P2P)的连接互相传输,很多网络问题容易被单一的测试环境忽略了。这也是为什么有些同学在自己的公司内网测试时候感觉延时小声音流畅,跑到真实环境下就经常遇到各种各样的质量问题。即时通讯聊天软件app开发可以加蔚可云的v:weikeyun24咨询

 

另外值得一提的是,除了在传输层引起的丢包抖动,最后一公里(Last Mile)的问题(路由器,移动数据网络等)也会引起丢包抖动,所以有时候有的同学说我们家20M的带宽,怎么用起来还是卡顿。其实有时候是因为你家路由器太破了。

设备对于音频质量的影响是相对隐性的,但是往往会起着决定性的作用。

iPhone就有着比较好的声学设计:

    麦克风和扬声器之间的耦合程度较小:
    这样你说话经扬声器播放产生的回声,在被麦克风收录时候已经有了很大程度的衰减,对回声消除模块来说也是一个利好。
    另外它有三个麦克风:
    位于设备底部的麦克风,主要收取说话人的声音;位于背部的麦克风,用来拾取背景噪声,给主麦克风做参考,从而更好对人声做降噪处理,让对方听得更清楚;位于听筒附近的麦克风,用来感知听筒附近的噪声,从而生成一个反相位的波从听筒里播放出来抵消这部分噪声,让你听对方也可以听的更清楚。


但是,设备的问题在安卓机上就非常碎片化,所有和安卓打过交道的开发者都没少听过适配这两字。由于每个设备扬声器和麦克风的属性都不尽相同,特别是在一些中低端机型上,声学设计是非常不合理的(严重的麦克风扬声器耦合,非线性失真,麦克风底噪等),会使得一些通用的音频算法(回声消除,降噪)无法正常工作。这也回答了我们之前的问题,为什么有些同学测的iPhone觉得不错,但是到一些中低端的安卓机器上就问题百出。这类问题无论网络好坏都会产生,这时候就必须有音频引擎的算法模块来做对应的算法适应和适配了。

除此之外,在手机这类非实时操作系统上,计算资源的抢占,录放音的调度问题都会对音频算法带来很大的挑战。要解决这些问题就必须投入大量的资源去研发和调试,而解决这类问题的技术门槛一般都是很高的。

物理环境对音频的影响更不容易被察觉,但是它在很多情况下会干扰到音频引擎的正常工作,从而对用户的最终听感产生负面影响。熟悉音频算法的朋友都知道,我们在做回声消除的时候,需要实时估计出当前物理环境的脉冲响应(Impulse response),才能将它和参考信号(Reference signal)卷积,从而初步估算出麦克风收到的回声信号。

假设我们现在身处一个密闭的会议室,扬声器播放出来的回声部分,在被麦克风收录时,就会掺入很多物理环境反射路径带来的分量,这个时候就要考察自适应滤波器是否有足够的能力来覆盖这种场景了。如果音频引擎做得不好,就会导致我们平时遇到的一些奇怪现象:比如为什么我刚才听对方好好的,他换了个小会议室继续开会,我就听到很多奇怪的杂音呢?事实上,影响脉冲响应的因素远不止这些,甚至有研究发现每一度温度的变化可能会导致40dB脉冲响应的变化。

另外还有很多物理环境会对音频质量造成影响,举例:

    近场时候的尖锐杂音(啸叫),是由于设备A的麦克风会直接收录到设备B的扬声器播放的声音,然后又会传回设备B播放出来,形成了一个正反馈回环导致的。只要分开一定距离通话或者静音掉其中一方就会消失。
    本地身处嘈杂的环境下的听对方会更困难,对方听自己也会有受到噪声的干扰。
    刚才说的密闭环境下,本身想保留的语音信号也会受到反射路径的影响,造成平时所说的混响(Reverb), 会让对方听到一些失真。
    网络,设备和物理环境都会对音频质量造成很大的影响,而且这种影响很多时候并非很直观的可以察觉到。如果没有科学的评估和定量的分析,很难通过一两次测试来下比较全面和准确的结论。


下一节会告诉你:我们需要怎样来定量和全面的评估一个音频引擎呢?要做哪些测试才能覆盖到尽量多的真是使用场景,同时又能尽可能的排除各种随机的影响因素呢?

我们想要定量的分析一个音频引擎的优劣点,就必须在测试中尽可能的排除网络、设备和物理环境等因素带来的随机性影响。3GPP、ESTI等通信业国际标准,对手机通信的测试环境方法很多要求和指引,感兴趣的同学可以在参考文献找到一些资料。

简单的说,我们需要:

    专业设计的消声室:我们需要足够安静且反射路径最小化的声学环境来避免周围的环境音来影响测试。
    人工耳和人工嘴:我们需要可重复又高保真的发声和收音装置来覆盖人的正常说话和听力动态范围。
    网损设备:为了覆盖更多的真实场景,我们需要网损设备来模拟和控制丢包。
    近似真实环境的沉浸式噪音场景:我们需要在人工头的四周布置高保真的音箱来制造噪声声场。

要执行符合3GPP,ETSI等通信标准的客观测试,我们需要搭建了类似下图的测试环境。以Head Acoustic的ACQUA系统为例,我们需要:

    将被测设备(DUT)置于消声室内,根据听筒,耳机和外放模式对应的标准距离和方法固定被测设备。
    参考设备(RD)放在消声室外,通过Line-in线从测量前端(MFE)输入标准的语音序列。
    做发送端的测量时,DUT接收到人工嘴的语音信号,经过对应的音频模块和网络传输处理,由消声室外的RD收到解码并送入MFE计算得分。
    做接收端的测量时,参考信号由MFE灌入RD,经过网络传输被DUT收到解码播放,人工耳记录下从DUT播放出来的声音与参考信号比较计算得分。
    网损模拟装置控制在发送端或者接收端加入不同类型的丢包,延时和抖动,来测量不利网络环境下的引擎表现。
    背景噪声模拟装置在消声室环境中制造不同信噪比和噪声类型的环境噪声,测试音频模块的降噪效果。

在业界,音频主观测试并没有可以统一遵循的标准。虽然ITU对音频主观测试有一些建议和指引,但是每个测试都有自身的侧重点设计和执行也不尽相同。一般比较常用的做法是请足够多的人来采集有统计意义的样本,然后对测试人员做一定的听音培训。最后根据信号失真度,背景侵入度,和总体质量等方面来对音频通话打分。

这种方法主要用来比较不同引擎之间的总体主观感受,如果需要更细节的发现和比较问题,还是需要跟针对性的测试。

主观测试相对来比较灵活,可以不必限定在消声室中进行。但是为了尽量避免我们之前的提到的设备网络环境的不确定因素,测试人员和被测设备需要分别放置于两个音源隔离的房间。网损的部分,可以使用Linux的TC NetEM模块模拟,如10%丢包设置命令为:tc qdisc add dev eth0 root netem loss 10%。 噪声的部分,如果没有ACQUA等分析系统提供的噪声源,可以使用NOISEX-92等学术研究中常用的语料库来代替。建议对通话进行录音,这样可以在测试后重听和标注,更好的分析问题。如果测试的引擎不带录音的话,可以在外放的而环境通过外部设备来录制。

一般我们先在较好的网络状态下测试音频的基础质量,然后慢慢增加丢包率来测试一个引擎抗丢包的边界。另外在细节的音频模块方面也需要很多针对性的测试,比如回声消除,降噪,增益控制,近场啸叫,盲源分离等模块都可以有非常详细的细节指标可以跟踪。

下图(a)和(b)比较了两款实时音频引擎(为了避免广告嫌疑,我们以引擎A和引擎B命名)在降噪(NS)方面的表现。这里用的是NOISEX-92语料库中的Voice Babble,混音的信噪比是5dB。 通过录音和定量分析,我们可以看到在算法的收敛时间,降噪后的残留噪声,和有语音时候的信噪比方面,引擎B的音频引擎效果有明显的优势。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/71447.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

【嵌入式硬件芯片开发笔记】EEPROM芯片M24C32配置流程

【嵌入式硬件芯片开发笔记】EEPROM芯片M24C32配置流程 32-Kbit serial IC bus EEPROM - 105C operation 适用于M24C32/M24C32-DRE 读取存储的从机地址为:0x50 读取标识页面的从机地址为:0x58 WC引脚接地,存储可以进行写操作 地址长度为16位 存…

117. 填充每个节点的下一个右侧节点指针 II

文章目录1. 背2. 题目3. 答案1. 背 这道题本来可以很简答,一个队列,存储指针和它的行数就OK了,但是这道题的难点在于不用额外空间复杂度。 横向看一下,这一行是不是就是一个链表呢? 多加一个变量,用来存储第…

C++入门教程||C++ 判断||C++ 日期 时间

判断结构要求程序员指定一个或多个要评估或测试的条件,以及条件为真时要执行的语句(必需的)和条件为假时要执行的语句(可选的)。 下面是大多数编程语言中典型的判断结构的一般形式: 判断语句 C 编程语言提…

three.js实战 -自定义剪切器

1. 前言 这是我在github上看到大佬的一个作品,当时感觉很有意思,决定分享出来,不知道取这个名字是否正确,废话不多说看下面效果。 2.demo效果 3.需要掌握的知识 矩阵的基本运算,能够认是到一些基本变换用到的矩阵(…

晶圆级倒装装备及控制系统

晶圆级倒装装备主要由晶圆盘进料模块、晶圆盘工作台模块、覆晶模块、焊头模块、基板工作台模块、点胶模块、视觉模块和基板进出料模块组成,如图 2-2 所示。 晶圆级倒装装备控制系统结构晶圆级倒装装备的运控系统主要由工控机、运动控制卡、驱动器、反馈装置和直线电…

QA:observable and Subject

概念区别和常见的错误理解辩证: 通俗理解一下 1. Observable 是一条 "水管蓝图" ,每次打开水龙头,水流会按照设计好的路线流向终点。起点和终点一一对应。每次打开水流,都是新的流,水流之间互不影响。一次一管。 2. …

VMWare虚拟机设置CentOS7共享文件夹

1. 目录 系统版本:CentOS 7.9 文章目录1. 目录2. VMWare:虚拟机设置,设置共享文件夹3. 虚拟机设置:手动挂载共享文件夹4. 检查是否挂载成功5. (可选)创建共享文件夹的软链接(快捷方式)6. (可选)定时任务开机自动挂载2. VMWare&am…

博客文章分类导引(持续更新)

摘要:本文提供一篇博客目录,有物联网、安卓编程、硬件设计等若干主题,这些主题一般都是成系统的,可以实现从零开始做出自己的物联网系统。 文章结构如下: 1.物联网专栏 使用arduino编写mqtt客户端连接emqx服务器 VSC…

vue.js:组件化的实现和使用过程

什么是组件化? 当我们遇到复杂问题的时候: 任何一个人处理信息的逻辑能力都是有限的所以,当我们面对一个复杂的问题的时候,我们不可能一次性搞定处理掉一大堆内容但是我们都会有问题拆解的能力将一个复杂的问题拆解成很多小的问…

Springcloud笔记之Ribbon

Ribbon:负载均衡(基于客户端)1. 负载均衡以及Ribbon1.1 Ribbon 的概念1.2 Ribbon 的作用2. 集成Ribbon3. 使用Ribbon实现负载均衡3.1 步骤3.2 自定义规则1. 负载均衡以及Ribbon 1.1 Ribbon 的概念 Spring Cloud Ribbon 是基于Netflix Ribbo…

[附源码]计算机毕业设计JAVA智能超市导购系统

[附源码]计算机毕业设计JAVA智能超市导购系统 项目运行 环境配置: Jdk1.8 Tomcat7.0 Mysql HBuilderX(Webstorm也行) Eclispe(IntelliJ IDEA,Eclispe,MyEclispe,Sts都支持)。 项目技术: SSM mybati…

WebRTC Native M96 回调音频裸数据IAudioFrameObserver--采集的音频(onRecordAudioFrame)

上篇已经说道,通过注册回调,给上层APP抛音频裸数据: 《WebRTC Native M96 SDK接口封装–注册语音观测器对象获取原始音频数据registerAudioFrameObserver》[https://dabaojian.blog.csdn.net/article/details/128218542] 此篇,就详细讲述一下,如果实现onRecordAudioFrame…

vue学习笔记(二)-vue生命周期

概念 a.又名生命周期回调函数、生命周期函数、生命周期钩子b.是什么:Vue在关键时刻帮我们调用的一些特殊名称的函数c.生命周期函数的名字不可更改,但函数的具体内容是程序员根据需求编写的d.生命周期函数中的 this 指向是vm或组件实例对象 示例代码&am…

来一场关于元宇宙可持续的灵魂辩论|BOOK DAO 内容共建 第6期 招募

小杜《元宇宙创意图谱》是 BOOK DAO 的共建书籍项目,12.03我们举行了虚拟时尚主题的第5次公开共建活动。本周六晚8点,我们将举办第6期 元宇宙可持续 专题的共建活动。BOOK DAO 以搭建产业界与用户之间的交流平台、挖掘业界最值得深入探讨研究的话题为目标…

【linux】ssh免密登录

概要 服务器免密登录实际上是基于公钥的认证,比如希望A服务器可以免密访问B服务器,则需要进行如下步骤 A服务器生成密钥对将A服务器生成的公钥分发到B服务器(写入~/.ssh/authorized_keys)A服务器即可免密登录B服务器 生成密钥对…

特殊类的设计(单类模式)

一.不能拷贝的类 首先要知道拷贝的场景:拷贝构造函数以及赋值运算符重载,想要让一个类禁止拷贝,只需让该类不能调用拷贝构造函数以及赋值运算符重载即可。 方法1:将这两个函数只声明,不定义(防止编译器默…

【愚公系列】2022年12月 Redis数据库-Cache和Redis缓存的无缝切换使用

文章目录前言一、Cache和Redis缓存的无缝切换使用1.安装包2.服务配置3.创建控制器4.启动程序前言 Redis是分布式缓存,是将数据随机分配到不同服务器的,catch属于单机缓存,只能本机访问。 Redis和Cache的区别吧 Redis和cache都是将数据存放…

Nginx rewrite 详解

Nginx rewrite 详解 本篇主要介绍 nginx 的 rewrite 重定向这个功能进行 详解介绍, 以及介绍它的使用场景 1. rewrite 基本介绍 rewrite是实现URL重写的关键指令,根据regex (正则表达式)部分内容,重定向到replacement,结尾是flag标记。 基本语法: re…

JAVA SCRIPT设计模式--结构型--设计模式之Decorator装饰模式(9)

JAVA SCRIPT设计模式是本人根据GOF的设计模式写的博客记录。使用JAVA SCRIPT语言来实现主体功能,所以不可能像C,JAVA等面向对象语言一样严谨,大部分程序都附上了JAVA SCRIPT代码,代码只是实现了设计模式的主体功能,不代…

JSP ssh房地产项目管理系统myeclipse开发mysql数据库MVC模式java编程计算机网页设计

一、源码特点 JSP ssh房地产项目管理系统是一套完善的web设计系统(系统采用ssh框架进行设计开发),对理解JSP java编程开发语言有帮助,系统具有完整的源代码和数据库,系统主要采用 B/S模式开发。开发环境为TOMCAT7…