H264的基本原理(三)------ H264结构与码流

上一篇:H264的基本原理(二)------ H264编码原理

1、H264的结构图

 

2、H264的编码分层

        H.264原始码流(裸流)是由一个接一个NALU组成,它的功能分为两层,VCL(视频编码层)和 NAL(网络提取层).

      (1)NAL层 (视频数据网络抽象层)

        因为H264最终还是要在网络上进行传输,在传输的时候,网络包的最大传输单元是1500字节,一个H264的帧往往是大于1500字节的,所以需要将一个帧拆成多个包进行传输。这些拆包、组包等工作都在NAL层去处理。

      (2)VCL层 (视频编码层)

        对视频的原始数据进行压缩。

3、码流的基本概念

        (1)SODB ,String Of Data Bits 原始数据比特流

        因为它是流的形式,所以长度不一定是8倍数,它是由 VLC 层产生的。由于我们计算机是以8倍数去处理数据所以计算机在处理H264时,就需要 RBSP。

        (2)RBSP,SODB + tailing bits (原始字节序列载荷)

        由于它是一个压缩流,SODB 不知道是在何处结束,所以算法在SODB最后一位补一个1,没有按字节对齐的则补 0。

        (3)EBSP (扩展字节序列载荷)

        在生成压缩流之后,在每一帧的开头加一个起始位,这个起始位一般是 00 00 00 01 或者是 00 00 01。所以在h264码流中规定每有两个连续的00 00,就增加一个0x03。

        补充:EBSP 和 RBSP的区别

        A、NALU的主体涉及到三个重要的名词,分别为EBSP、RBSP和SODB。其中EBSP完全等价于NALU主体,而且它们三个的结构关系为:EBSP包含RBSP,RBSP包含SODB。

        在h264的文档中,并没有EBSP这一名词出现,但是在h264的官方参考软件JM里,却使用了EBSP。NALU的组成部分为:

        NALU = NALU Header + RBSP

        其实严格来说,这个等式是不成立的,因为RBSP并不等于NALU刨去NALU Header。严格来说,NALU的组成部分应为:

        NALU = NALU Header + EBSP

        其中的EBSP为扩展字节序列载荷(Encapsulated Byte Sequence Payload),而RBSP为原始字节序列载荷(Raw Byte Sequence Payload)

         B、那为什么要弄一个EBSP呢?

        EBSP相较于RBSP,多了防止竞争的一个字节:0x03。

        我们知道,NALU的起始码为0x000001或0x00000001,同时H264规定,当检测到0x000000时,也可以表示当前NALU的结束。那这样就会产生一个问题,就是如果在NALU的内部,出现了0x000001或0x000000时该怎么办?

        所以H264就提出了“防止竞争”这样一种机制,当编码器编码完一个NAL时,应该检测NALU内部,是否出现如下左侧的四个序列。当检测到它们存在时,编码器就在最后一个字节前,插入一个新的字节:0x03。

        这样一来,当我们拿到EBSP时,就需要检测EBSP内是否有序列:0x000003,如果有,则去掉其中的0x03。这样一来,我们就能得到原始字节序列载荷:RBSP。

 

        (4)NALU(NAL Unit)

        在EBSP的基础上,加1字节的NAL 头

        NAL Header(1B) + EBSP

 

4、NAL Unit

        如上图所示,生成的H264视频帧是由多个切片组成的。一个H264的帧至少由一个切片组成,不能没有切片,可以是一个到多个不能没有。在网络传输的时候一个H264帧可能需要切开去传,一个一次传不完,这就按照切片来切。每一个切片组成一个NAL Unit。

 

5、切片 与 宏块的关系

 

宏块分类 意义
mb_type(宏块类型) 确定该 MB 是帧内或帧间(P 或 B)编码模式,确定该 MB 分割的尺寸
mb_pred(宏块的预测) 确定帧内预测模式(帧内宏块)确定表 0 或表 1 参考图 像,和每一宏块分割的差分编码的运动矢量(帧间宏块,除 8×8 宏块分割的帧内 MB)
sub_mb_pred (只对 8×8MB 分割的帧内 MB)确定每一子宏块的子宏 块分割,每一宏块分割的表 0 和/或表 1 的参考图象;每一 宏块子分割的差分编码运动矢量。
coded_block_pattern 指出哪个 8×8 块(亮度和彩色)包 编码变换系数
mb_qp_delta 量化参数的改变值
residual(残差数据) 预测后对应于残差图象取样的编码变换系数

        在切片数据中,包含若干个宏块。在一个宏块中,又包含了宏块类型、宏块预测、残差数据。

 

5、切片 与 宏块的关系

        H264码流的分层结构,如图:

        1帧 = n个片
        1片 = n个宏块
        1宏块 = 16x16yuv数据
 

内容参考:

1.【H264/AVC 句法和语义详解】(三)

2. 向晨宇的技术博客从零了解H264结构

 

下一篇

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章