文章目录
- 1.什么是GOP?
- 1.1 GOP介绍
- 1.2.GOP中I帧/B帧/P帧
- 1.3.I帧和IDR的区别联系
- I帧(Intra Frame)
- IDR帧(Instantaneous Decoding Refresh Frame)
- 区别总结
- 1.4 帧与分组的关系
- 1.5 SPS与PPS
- SPS(Sequence Parameter Set)
- PPS(Picture Parameter Set)
- SPS与PPS的关系
- 2.宏块
- 2.1宏块的定义
- 2.2宏块的组成
- 2.3宏块的划分过程
- 划分子块
- 2.4宏块的重要性
- 3.帧内压缩
- 3.1帧内压缩的基本原理
- 3.2帧内预测模式
- 3.3帧内预测举例
- 4.帧间压缩
- 帧间压缩的基本原理—运动估计和运动补偿
- 帧间压缩中的帧类型
- 参考文献
1.什么是GOP?
1.1 GOP介绍
GOP(Group of Pictures,图像组)是视频编码中的一个重要概念,特别是在H.264等视频压缩标准中。GOP定义了一组连续的图像帧,包括一个关键帧和后续的一些预测帧。这些帧一起构成一个编码单位。这一组帧是关联性比较强的一组帧,比如下图,玩电脑的相关画面比较相似,可以定义为一组帧,拿望远镜的一组画面关联性比较强, 可以定义为一组帧。
换另一个角度,GOP之间的画面都是比较相似的,有关联性,而且帧之间的差别比较小。比如下图,这组画面都是小人站着,只是拿望远镜的姿势不一样
1.2.GOP中I帧/B帧/P帧
- 关键帧(I帧):完全独立压缩的帧,不依赖于其他帧的数据。这些帧包含完整的图像信息,是解码的基础。
- 预测帧(P帧):基于前一个I帧或P帧进行压缩,存储的是与前一帧的差异信息。它的大小占I帧的一半,采用帧间压缩技术。
- 双向预测帧(B帧):基于前后的I帧或P帧进行压缩,存储的是前后帧之间的差异信息。它的大小占帧的四分之一,采用帧间压缩技术。
GOP通常定义为一个I帧后跟随若干个P帧和B帧的结构,
例如一个常见的GOP结构可能是“IBBPBBPBBPBBI”。在这个例子中,每隔12帧会有一个新的I帧。此时这里GOP开头的是IDR帧,一种特殊的I帧。
- GOP长度:GOP的长度指的是从一个I帧到下一个I帧之间的总帧数。GOP长度越长,压缩效率越高,因为I帧数量减少,但解码复杂度和对网络丢包的敏感性也增加。
- GOP结构选择:短GOP(更多的I帧)适用于需要频繁随机访问的场景,如视频编辑。长GOP(更多的P帧和B帧)适用于流媒体和存储场景,因其更高的压缩效率。
虽然说B帧的在GOP中占的空间很小,但并不是越多越好。原因有以下几点:
-
编码和解码复杂度:B帧的编码和解码需要参考前后的多个帧,因此会增加编码器和解码器的计算复杂度。过多的B帧会导致解码器的处理负担增加,可能对硬件性能提出更高的要求。
-
延迟:B帧的使用会增加编码和解码的延迟,因为解码一个B帧需要解码它所参考的前后的帧。在实时应用(如视频通话和直播)中,过多的B帧可能会导致明显的延迟,影响用户体验。
-
错误传播:B帧依赖于前后的帧,如果参考帧受到损坏(例如在传输过程中丢失数据),错误会传播到依赖这些参考帧的B帧,影响视频质量。
-
灵活性和随机访问:更多的B帧可能会降低视频的灵活性,例如在快速场景切换或需要随机访问视频的情况下,过多的B帧可能不利于快速跳转和重构图像。
如果在对实时性要求比较苛刻的情况下,一般会减少B帧,甚至不用B帧,这样可以加快解码速度,及时播放。
1.3.I帧和IDR的区别联系
IDR帧(Instantaneous Decoding Refresh frame)和I帧(Intra frame)都是关键帧,但它们有一些重要的区别和各自的用途:
I帧(Intra Frame)
- 定义:I帧是一种独立压缩的帧,它不依赖于其他帧进行解码,包含了完整的图像信息。
- 用途:I帧作为参考帧用于预测后续的P帧和B帧。因此,解码一个I帧就可以得到一幅完整的图像。
- 位置:I帧可以出现在视频流的任何位置,通常在GOP(图像组)开始时。
- 关键点:I帧是用来提高视频的压缩效率和质量的,因为它们提供了完整的图像信息。
IDR帧(Instantaneous Decoding Refresh Frame)
- 定义:IDR帧是一种特殊类型的I帧,它不仅包含完整的图像信息,还具有刷新解码器状态的作用。
- 用途:当解码器遇到一个IDR帧时,它会丢弃之前所有未解码的帧并开始新的序列解码。这意味着IDR帧后面的所有帧不会依赖于IDR帧前面的任何帧。
- 位置:IDR帧通常用于切换场景、章节或在需要完全重新开始解码的情况下使用。
- 关键点:IDR帧使解码器能够在视频流中找到一个新的起点,适用于断点续播或随机访问视频的场景。
区别总结
- 依赖关系:I帧是独立的帧,但它们后的帧(P帧和B帧)可以依赖于它们。而IDR帧不仅是独立的帧,且在它之后的帧都不会依赖于它之前的任何帧。
- 解码器刷新:遇到IDR帧时,解码器状态会被刷新,丢弃之前的所有数据。这使得IDR帧成为视频流中的一个新的起点。I帧则没有这个功能。
- 应用场景:I帧主要用于常规的GOP结构中以提高压缩效率。IDR帧则用于需要重新开始解码的情况,如场景切换或随机访问。
1.4 帧与分组的关系
参考关系:在一个GOP内,P帧和B帧分别参考前面的I帧或P帧(P帧)和前后的I帧或P帧(B帧)。这种参考关系使得帧之间的差异信息可以有效压缩,提高了编码效率。
解码顺序:虽然帧在编码时按时间顺序排列,但在解码时,参考帧(如I帧和P帧)必须先解码,以便后续的B帧能够正确解码。这意味着解码顺序与显示顺序不同。
独立性:IDR帧在GOP中的作用尤为重要,它使得后续帧的解码不依赖于之前的帧,从而允许在视频流中进行快速跳转和重建解码器状态。
这里需注意:解码的时候先解码I帧和P帧,最后解码B帧,B帧参考I帧和P帧,B帧不参考B帧
1.5 SPS与PPS
在H.264视频编码标准中,SPS(Sequence Parameter Set,序列参数集)和PPS(Picture Parameter Set,图像参数集)是两个重要的参数集,它们用于描述视频序列的全局和局部参数设置。
SPS(Sequence Parameter Set)
定义:SPS包含描述视频序列全局属性的参数,这些属性适用于整个视频流或视频序列中的所有帧。
内容:
- 图像的宽度和高度
- 帧率(时间信息)
- 编码配置文件和级别
- 颜色格式和色度取样
- 参考帧的最大数量
- 视频格式(如帧结构或场结构)
作用:SPS为解码器提供了解码整个视频序列所需的全局信息。每个解码器在开始解码视频流时都需要读取和解析SPS,以便了解如何正确解码后续的帧。
PPS(Picture Parameter Set)
定义:PPS包含描述特定图片或一组图片(如一个GOP)的参数,这些参数可以在SPS定义的全局参数基础上进一步细化。
内容:
- 量化参数
- 去块效应滤波器参数
- 变换系数和预测模式
- 参考帧的使用方式
- 局部帧率调整
作用:PPS提供了在解码特定图片或图片组时所需的详细信息。它允许编码器在需要时调整每个图片的解码参数,以实现更好的压缩效果和解码性能。
SPS与PPS的关系
- 层级结构:SPS定义了全局参数,适用于整个视频序列,而PPS定义了特定图片或图片组的参数,适用于由SPS定义的基础上的局部调整。解码器首先读取SPS以了解视频序列的全局设置,然后读取PPS以获取每个图片或图片组的具体参数。
- 多样性:一个视频序列中可以有多个SPS和PPS。编码器可以在不同的时间使用不同的SPS和PPS,以优化不同场景的编码质量。例如,复杂场景可能需要不同的量化参数和滤波器设置。
在很多视频流应用中,每个IDR帧之前通常会包含SPS和PPS。这是为了确保解码器在接收到IDR帧时,能够正确解码帧。由于IDR帧会刷新解码器状态并使后续帧不依赖于之前的任何帧,因此在IDR帧之前传输SPS和PPS有助于保证解码器能够从IDR帧开始正确解码。
2.宏块
在H.264视频编码技术中,“宏块”(Macroblock)是视频帧的基本编码单元。宏块的概念和处理方式对于理解H.264编码的压缩效率和图像质量至关重要。以下是对宏块的详细解释:
2.1宏块的定义
宏块是一个固定大小的矩形区域,通常为16x16像素。在一些高配置文件中,宏块可能会被进一步分割为更小的块,但16x16像素是标准的基础单位。每个宏块包含亮度(Luma)和色度(Chroma)信息,具体如下:
- 亮度(Luma):描述图像的亮度部分。
- 色度(Chroma):描述图像的色彩部分,通常分为两个分量(Cb和Cr)。
2.2宏块的组成
-
亮度(Luma)分量:
- 一个宏块包含16x16个亮度像素。
-
色度(Chroma)分量:
- 由于色度通常以较低分辨率采样,宏块中的色度信息取决于采样格式(如4:2:0、4:2:2、4:4:4等)。
- 在4:2:0采样格式中,色度分量的采样率是亮度的1/4,因此每个宏块包含8x8个Cb和8x8个Cr色度像素。
2.3宏块的划分过程
宏块可以根据内容的复杂度进一步分割为更小的块(如8x8、8x4、4x8、4x4等)。这种分割方式允许编码器更灵活地适应图像的细节和运动。
比如下方原始图片
在左上角划分一块8x8的宏块,右侧是宏块的具体像素值的体现
计算完所有的图像的宏块之后,如下
划分子块
H264对比较平坦的图像使用 16X16 大小的宏块。但为了更高的压缩率,还可以在 16X16 的宏块上更划分出更小的子块。子块的大小可以是 8X16、 16X8、 8X8、 4X8、 8X4、 4X4非常的灵活。
下方图片中,红框内的 16X16 宏块中大部分是蓝色背景,而三只鹰的部分图像被划在了该宏块内,为了更好的处理三只鹰的部分图像,H264就在 16X16 的宏块内又划分出了多个子块。
这样再经过帧内压缩,可以得到更高效的数据。下图是分别使用mpeg-2和H264对上面宏块进行压缩后的结果。其中左半部分为MPEG-2子块划分后压缩的结果,右半部分为H264的子块划压缩后的结果,可以看出H264的划分方法更具优势。
- 预测:
- 帧内预测(Intra Prediction):在同一帧内,通过参考邻近已编码块来预测当前宏块。
- 帧间预测(Inter Prediction):通过参考之前或之后的帧来预测当前宏块,这种方法利用了帧之间的时间冗余。
- 变换和量化:
- 预测误差块进行离散余弦变换(DCT)以转换为频域表示,然后进行量化以减少数据量。
- 熵编码:
- 量化后的系数使用熵编码(如CAVLC或CABAC)进行压缩,进一步减少数据量。
2.4宏块的重要性
-
压缩效率:
- 宏块的分割和预测机制显著提高了压缩效率,使得H.264在保持高视频质量的同时,能够大幅减少视频数据量。
-
灵活性:
- 通过灵活的宏块分割和预测方式,H.264能够有效适应各种视频内容,从低复杂度的平滑区域到高复杂度的细节丰富区域。
-
编码性能:
- 宏块处理是H.264编码器和解码器的核心,决定了编码效率、图像质量和处理复杂度。
3.帧内压缩
3.1帧内压缩的基本原理
帧内压缩通过预测图像块的像素值并仅存储预测误差来实现数据压缩。它主要包括以下步骤:
- 帧内预测(Intra Prediction):
- 帧内预测利用当前帧中已解码的相邻像素块来预测当前块的像素值。通过预测,编码器可以显著减少需要存储的数据量。
- 帧内预测模式包括多种方向预测方式,如水平、垂直、对角线等。不同的预测模式适用于不同类型的图像内容。
- 变换和量化:
- 预测误差块通过变换(通常是整数离散余弦变换,Integer Discrete Cosine Transform,DCT)转换到频域。变换后的系数表示块内的频率成分。
- 变换后的系数进行量化,量化过程减少了数据的精度,从而进一步压缩数据量。量化过程会引入一定的损失,但这些损失通常是人眼难以察觉的。
- 熵编码(Entropy Coding):
- 量化后的系数通过熵编码(如上下文自适应可变长编码,CAVLC,或上下文自适应二进制算术编码,CABAC)进行压缩。熵编码根据系数的统计特性分配较短的码字给频繁出现的符号,从而进一步减少数据量。
3.2帧内预测模式
H.264中的帧内预测模式一共有九种,常见的有以下几种:
- 4x4帧内预测:
- 用于亮度块(Luma)的预测,共有9种模式,包括垂直预测、水平预测、DC预测(平均值预测)和若干对角线预测模式。
- 8x8帧内预测:
- 高级配置文件(High Profile)中的预测模式,提供了更多的细粒度预测选项,适用于高清内容。
- 16x16帧内预测:
- 用于较大亮度块的预测,共有4种模式:垂直、水平、DC和平面预测。适用于较大且平滑的图像区域。
- 色度预测(Chroma Prediction):
- 色度块的预测模式与16x16亮度块的预测模式类似,包含垂直、水平、DC和平面预测。
3.3帧内预测举例
对上图中的红色方面部分进行预测
左边为原始数据,对红框部分根据周边的宏块进行预测,右边使用4x4 亮度块预测模式,右侧红框为预测结果,可以看出区别不大,通过预测可以大大减少压缩量。但是仅仅是使用预测模式的话,仍然会有细微差别,比如说下图
大体上是还原出来了,但仍然有些差距。此时可以进行残差值的计算。残差值是实际像素值与预测像素值之间的差异。它反映了预测与实际值之间的误差。在帧内预测中,通过减去预测像素值得到残差值,然后对残差值进行变换和编码,以达到压缩数据的目的。通过对比残差值就可以还原预测模式与实际图片的差距。最终基本上还原出原始图片
帧内压缩的数据 = 帧内预测数据+残差值的压缩数据。左边是原始的数据,右侧是预测结果+压缩的残差数据。
4.帧间压缩
利用视频帧之间的时间冗余来实现高效的数据压缩。帧间压缩通过参考其他帧来预测当前帧的内容,从而减少需要编码和传输的数据量。
帧间压缩的基本原理—运动估计和运动补偿
帧间压缩的核心思想是利用相邻帧之间的相似性,通过运动估计和运动补偿技术来预测当前帧的内容。具体过程如下:
-
运动估计(Motion Estimation):
运动估计是确定当前帧中的宏块在参考帧中的位置。这个过程找到一个运动矢量(Motion Vector),描述宏块从参考帧到当前帧的位置变化。
以台球运动为例,下面是一组相关性比较强的帧,即GOP。
H264编码器会按顺序依次逐行扫描,每次取出两幅相邻的帧进行宏块比较,计算两帧的相似度。如下图:
通过宏块扫描与宏块搜索可以发现这两个帧的关联度是非常高的。进而发现这一组帧的关联度都是非常高的。因此,上面这几帧就可以划分为一组。其算法是:在相邻几幅图像画面中,一般有差别的像素只有10%以内的点,亮度差值变化不超过2%,而色度差值的变化只有1%以内,我们认为这样的图可以分到一组。
在这样一组帧中,经过编码后,我们只保留第一帖的完整数据,其它帧都通过参考上一帧计算出来。我们称第一帧为IDR/I帧,其它帧我们称为P/B帧,这样编码后的数据帧组我们称为GOP。
分完组,就可以计算运动矢量了。H264编码器首先按顺序从缓冲区头部取出两帧视频数据,然后进行宏块扫描。当发现其中一幅图片中有物体时,就在另一幅图的邻近位置(搜索窗口中)进行搜索。如果此时在另一幅图中找到该物体,那么就可以计算出物体的运动矢量了。下面这幅图就是搜索后的台球移动的位置。
根据位置的差距,就可以计算出台球运动方向和距离来了。H264依次把每一帧中的球移动的距离和方向(运动矢量)记录下来。
-
运动补偿(Motion Compensation):
运动矢量计算出来后,将相同部分(也就是绿色部分)减去,就得到了补偿数据。我们最终只需要将补偿数据进行压缩保存,以后在解码时就可以恢复原图了。运动补偿生成的预测块与当前块之间的差值称为残差值(Residuals)。
-
残差值计算和编码:
- 残差值表示当前块与预测块之间的差异,残差值经过变换(如DCT或整数DCT)、量化和熵编码后进行压缩。
- 这种方法只需要传输运动矢量和残差值,大大减少了数据量。
帧间压缩中的帧类型
H.264中主要有三种帧类型,分别用于不同的帧间压缩策略:
-
I帧(Intra-coded Frame):
- 只使用帧内压缩技术,不依赖其他帧。I帧提供了随机访问点,允许解码器从此帧开始解码。
-
P帧(Predicted Frame):
- 使用之前的I帧或P帧作为参考帧进行预测和补偿。P帧的运动矢量和残差值编码相对较少,压缩效率较高。
-
B帧(Bi-predictive Frame):
- 使用前后两帧作为参考帧进行预测和补偿。B帧可以获得更高的压缩效率,但编码和解码复杂度较高。
参考文献
最通俗易懂的H264基本原理
宏块划分原理