前言
H264 视频压缩算法现在无疑是所有视频压缩技术中使用最广泛,最流行的。随着 x264/openh264 以及 ffmpeg 等开源库的推出,大多数使用者无需再对H264的细节做过多的研究,这大降低了人们使用H264的成本。
但为了用好 H264,我们还是要对 H264 的基本原理弄清楚才行。今天我们就来看看H264 的基本原理。
H264概述
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-ND3fMchH-1608540503819)(https://upload-images.jianshu.io/upload_images/24944255-da42799d87d8482b.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240)]
H264压缩技术主要采用了以下几种方法对视频数据进行压缩。包括:
- 帧内预测压缩,解决的是空域数据冗余问题。
- 帧间预测压缩(运动估计与补偿),解决的是时域数据冗徐问题。
- 整数离散余弦变换(DCT),将空间上的相关性变为频域上无关的数据然后进行量化。
- CABAC压缩。
经过压缩后的帧分为:I帧,P帧和B帧:
- I帧:关键帧,采用帧内压缩技术。
- P帧:向前参考帧,在压缩时,只参考前面已经处理的帧。采用帧音压缩技术。
- B帧:双向参考帧,在压缩时,它即参考前而的帧,又参考它后面的帧。采用帧间压缩技术。
除了I/P/B帧外,还有图像序列GOP。
- GOP:两个I帧之间是一个图像序列,在一个图像序列中只有一个I帧。如下图所示:
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-7oDJR6mL-1608540503824)(https://upload-images.jianshu.io/upload_images/24944255-2695e751eab6dfd4.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240)]
下面我们就来详细描述一下H264压缩技术。
H264压缩技术
H264的基本原理其实非常简单,下我们就简单的描述一下H264压缩数据的过程。通过摄像头采集到的视频帧(按每秒 30 帧算),被送到 H264 编码器的缓冲区中。编码器先要为每一幅图片划分宏块。
以下面这张图为例:
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-8ROx36Cy-1608540503826)(https://upload-images.jianshu.io/upload_images/24944255-e0747887a7bb7448.jpeg?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240)]
划分宏块
H264默认是使用 16X16 大小的区域作为一个宏块,也可以划分成 8X8 大小。
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-OVsdtFn6-1608540503829)(https://upload-images.jianshu.io/upload_images/24944255-e70c8be50e33b9c2.jpeg?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240)]
划分好宏块后,计算宏块的象素值。
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-2cbCrzL6-1608540503833)(https://upload-images.jianshu.io/upload_images/24944255-248e49d8d6041468.jpeg?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240)]
以此类推,计算一幅图像中每个宏块的像素值,所有宏块都处理完后如下面的样子。
划分子块
H264对比较平坦的图像使用 16X16 大小的宏块。但为了更高的压缩率,还可以在 16X16 的宏块上更划分出更小的子块。子块的大小可以是 8X16、 16X8、 8X8、 4X8、 8X4、 4X4非常的灵活。
上幅图中,红框内的 16X16 宏块中大部分是蓝色背景,而三只鹰的部分图像被划在了该宏块内,为了更好的处理三只鹰的部分图像,H264就在 16X16 的宏块内又划分出了多个子块。
这样再经过帧内压缩,可以得到更高效的数据。下图是分别使用mpeg-2和H264对上面宏块进行压缩后的结果。其中左半部分为MPEG-2子块划分后压缩的结果,右半部分为H264的子块划压缩后的结果,可以看出H264的划分方法更具优势。
宏块划分好后,就可以对H264编码器缓存中的所有图片进行分组了。
帧分组
对于视频数据主要有两类数据冗余,一类是时间上的数据冗余,另一类是空间上的数据冗余。其中时间上的数据冗余是最大的。下面我们就先来说说视频数据时间上的冗余问题。
为