网络抖动Jitter详解

在前文中介绍了RTT计算原理及其应用 。下面介绍网络抖动Jitter原理、计算方法以及在Webrtc中的应用 。
什么是抖动?在网络传输中 , 每个包从发送端到接收端的时延都是不相同的 , 而Jitter就是用来衡量这种不同 。一般在发送端 , 数据包发送时间间隔是相同的 , 也就是均匀发送数据 , 但是传输过程中由于各种情况 , 例如拥塞 , 丢包 , 网络错误等 , 接收端收到的数据包间隔就会不一样 , 可能一会大 , 一会小 , 导致时延发生变化 , 这个时延的变化程度就是所谓的抖动 。网络中存在抖动会导致接收端收包不均匀、甚至乱序 , 如果按照收包顺序去播放 , 对于视频而言 , 会导致帧率变化 , 视频播放就不平滑 , 有卡顿感 。对于音频而言 , 肯定会有时快时慢、来不及播放导致卡顿、错音等问题 , 在比较差的网络场景中语音基本是没法听 。接收端如果不做任何处理 , 就会影响用户体验 。
WebRTC针对网络抖动问题 , 根据音视频分为:NetEQ与JitterBuffer2种 , 分别对音频、视频进行抖动处理 , 消除抖动造成的影响 , 这些会在我的后续文章介绍 。
按照抖动的频率 , 也可以分为:
稳定抖动:这种抖动是网络和算法固有属性导致的 , 有一定的统计上的稳定性 , 在一段时间内呈现统计上的稳定性;
【网络抖动Jitter详解】突发抖动:这些抖动是在稳定抖动基础上叠加上突发的抖动尖峰 , 突发通常没有太大规律 , 无法找到统计上的规律性 。
一般的Jitter算法都是尽力去解决稳定抖动 , 对于突发抖动解决的并不是太好 。
如下图片是抖动的一个形象描述 。

网络抖动Jitter详解

文章插图
图1 -Jitter
如何计算抖动?假设RTP中第i包中记录的时间戳为Si(单位为采样率) , 到达接收端的时间为Ri(单位同样为采样率) , 如果Si代表第i个包的发送时间戳 , Ri代表第i个包的接收时间戳 。Sj、Rj同理 。
网络抖动Jitter详解

文章插图
图2 - Jitter计算原理图
抖动(i, j) = |(Rj - Ri) - (Sj - Si)| = |(Rj - Sj) - (Ri - Si)| (1)
WebRTC为了统一抖动 , 并且为了很好地降噪、降低突发抖动的影响 , 把上面的抖动(i, j)定义为D(i, j) , 抖动J(i)定义为:
J(i) = J(i-1) + (|D(i-1, i)| - J(i - 1)) / 16 (2)
增益参数1/16是为了消除噪声影响 , 使抖动收敛在较合理范围内 , 避免突发数据的影响 。从上一个公式中可以看到D(i-1, j)是唯一引起J(i)变化的因素 。
WebRTC统计参数中的抖动计算代码位于
StreamStatisticianImpl::UpdateJitter中
网络抖动Jitter详解

文章插图
图3 - 代码
time_diff_samples =|D(i−1,i)| (3)
J(i) = J(i-1) + (time_diff_samples - J(i - 1)) / 16 (4)
网络抖动Jitter详解

文章插图
图4 - 代码
至此我们得到了jitter_diff_q4 , 单位为采样率 , 如果需要转换为毫秒时间单位 。由于jitter_diff_q4放大了16倍 , 首先需要还原回去jitter = jitter_q4_ >> 4;转换为毫秒单位:jitter_ms = jitter / (clockrate_hz / 1000)(一般视频的时钟采样频率clockrate_hz为:90kHz) 。jitter_ms就是得到的毫秒级别的抖动 。




    推荐阅读