代码改变世界

I帧、B帧、P帧、NALU类型

2018-07-08 23:51  ljtcnblogs  阅读(8246)  评论(0编辑  收藏  举报

i帧 i frame,即内部画面 intra picture,通常是GOP的第一个帧(即IDR)
I帧是最大去除图像空间冗余信息而压缩得到的帧,自带全部信息,不参考其他帧可独立解码,称为帧内编码帧
所有视频至少包含一个I帧,且作为文件的第一个帧,文件里的其他的I帧用来改善视频质量,但增加了文件大小
一般而言,每秒视频至少需要1个I帧,每秒里增加I帧可以改善质量,但增加网络带宽和网络负载
视频播放过程中,若I帧丢失,则随后的P帧也就无法解析,所以出现黑屏现象,若P帧丢失,则出现花屏、马赛克现象

P帧,前向搜索帧/前向预测帧,以I帧预测P帧

B帧,双向搜索帧/双向内插帧,由I帧、P帧预测B帧


P帧压缩:根据本帧与相邻的前一帧(I帧或P帧)的不同点来压缩本帧数据
P帧重构:以前面相邻I帧为参考帧,计算P帧某点的预测值和运动矢量得到P帧某点样值
B帧压缩:根据本帧与相邻的前一帧的差值、本帧与相邻的后一帧的差值来压缩本帧数据
B帧重构:以相邻的前面相邻帧(I或P)、后面相邻帧(P)为参考,找出B帧某点的预测值和两个运动矢量得到B帧某点样值

I帧编码减少空间域冗余,P、B帧编码减少时间域冗余

NTSC = national television system committee 应用于美国、日本、加拿大、墨西哥等
PAL  = phase alternating line 应用于中国、香港、中东、欧洲
GOP  = group of pictures  其最大可含帧数量 18(NTSC)/15(PAL)
GOP是有固定模式的一系列I、P、B帧组成
常用结构由15帧(PAL)组成,具有以下形式IBBPBBPBBPBBPBB,简称GOP(4,2),指的是该图像组除了1个I帧外,包含4个P帧,且
任何相邻I、P之间或相邻P、P之间存在2个B帧

IDR  = instantaneous decoding refresh 即时解码刷新  IDR一定是I帧,但I帧不一定是IDR
为了区分帧序列的首个I帧和其他I帧,才定义首个I帧为IDR,解码器只可以从IDR开始解码,IDR表示一组新的帧序列GOP
在IDR帧之后的所有帧都不能引用该IDR之前的帧数据,在普通I帧之后的B、P帧可以引用该普通I帧之前的I帧
ID会导致DPB(decord picture buff 参考帧列表)清空,导致PPS、SPS参数更新

 

H264从结构上分为 视频编码层VCL(video coding layer)和网路抽象层NAL(network abstract layer)

VCL包括codec编解码功能(基于宏块模型)、运动补偿预测处理、循环过滤器处理

NAL把VCL的输出封装成NALU(网络抽象层单元),以适应基于包的网络传输或面向包的多路复用环境

 

NALU的第1个字节是NUAL类型字节,其格式如下

|0 |1 |2 |3 |4 |5 |6 |7 |

|F |NRI|Type              |

F:       1 bit  forbidden_zero_bit H.264规范声明值设置为1表示语法违例

NRI:  2 bit  nal_ref_idc 表示NALU的优先级。0--3,取值越大,该NALU越重要,需要优先保护

                                      00值表示该NALU不用于帧间图像预测重构参考图像,可以丢弃不用冒参考图像完整性风险。

                                      如果NALU是参考帧slice、PPS、SPS时,该值必须大于0

Type: 5 bit  nal_unit_type 表示NALU载荷类型,类型值定义如下

                                         0:未定义

                                         1:非IDR图像不采用数据划分片段

                                         2:非IDR图像采用数据划分片段A部分

                                         3:非IDR图像采用数据划分片段B部分

                                         4:非IDR图像采用数据划分片段C部分

                                         5:IDR图像片段

                                         6:补充增强信息 SEI

                                         7:序列参数集 SPS

                                         8:图像参数集 PPS

                                         9:分隔符

                                         10:序列结束符

                                         11:流结束符

                                         12:填充数据

                                         13:序列参数集扩展

                                         14:带前缀的NALU

                                         15:子序列参数集

                                         16-18:保留

                                         19:不采用数据划分的辅助编码图像片段

                                         20:编码片段扩展

                                         21-23:保留

                                         24-31:未定义

h264数据帧的NALU前面带有 00 00 00 01或 00 00 01 分隔符,一般VCL输出首帧数据为PPS、SPS,接着是IDR帧

00 00 00 01 67 SPS 00 00 00 01 68 PPS 00 00 00 01 65 IDR ... ...

分隔符作为NALU的开始边界和结束边界,解码器使用分隔符逐个字节匹配数据流,计算NALU的长度,然后开始解码

 

h264 序列、帧、slice关系

从大到小依次为:序列、帧(I、P、B帧)、片组、片(I、P、B、SP、SI片)、NALU、宏块、亚宏块、块、像素

 

序列

图像以序列为单位进行组织,GOP,序列就是一段连续图像帧且画面之间变化不大。

统计一段时间内图像的结果表明,相邻几幅图像,一般像素存在差别的点只有10%以内,亮度差值变化不超过2%,

色度差值变化只有1%以内。所以一段连续的图像画面之间变化不大,可以把第1帧编码为完整图像帧,第2帧只编

码其与前面一帧的差别,这样第2帧只是前一帧的1/10或更小,依次对第2帧之后的图像帧做同样处理,这样的一段

图像就是一个序列。当某个帧与前面的帧图像变化很大,无法参考前面帧生成时,就要开始一个新序列。

 

帧      :有1个或多个片组,如果不采用FMO(灵活宏块排序)机制,则一帧只有一个片组

片组  :包含1个片(slice)或多个片

片      :slice,由宏块组成,如果不采用DP(数据分割)机制,1个片只包含1个NALU,

               否则1个片由3个NALU组成,nal_unit_type值等于2、3、4的NALU属于同一个片

               分片的目的是限制误码的扩撒和传输,使片间保持独立,[ [slice header] [slice data] ]

               [slice header] 说明了片类型、属于哪个帧、参考帧等

               [slice data] 里是整数个宏块

宏块   :编码处理的基本单元,由多个块组成,通常宏块大小为16X16像素,分为I、B、P宏块

块       :一个编码图像要划分成多个块才能进行处理,一个块是4X4像素

图像解码过程是按照slice进行解码,然后按照片组将解码宏块重组成图像