DC系数和AC系数

来源:互联网 发布:es6 数组的遍历 编辑:程序博客网 时间:2024/04/29 13:42

转载自:http://www.itwendao.com/article/detail/280816.html       IT问道 谢谢


DC系数:  直流系数            AC系数:交流系数


1DC系数的中间格式计算

        JPEG中为了更进一步节约空间,并不直接保存数据的具体数值,而是将数据按照位数分为16组,保存在表里面。这也就是所谓的变长整数编码VLI。即,第0组中保存的编码位数为0,其编码所代表的数字为0;第1组中保存的编码位数为1,编码所代表的数字为-1或者1......,如下面的表格所示,这里,暂且称其为VLI编码表

       

前面提到的那个DC差值为3的数据,通过查找VLI可以发现,整数3位于VLI表格的第2组,因此,可以写成2)(3)的形式,该形式,称之为DC系数的中间格式。

2AC系数的行程长度编码(RLC)

        量化之后的AC系数的特点是,63个系数中含有很多值为0的系数。因此,可以采用行程编码RLCRun Length Coding)来更进一步降低数据的传输量。利用该编码方式,可以将一个字符串中重复出现的连续字符用两个字节来代替,其中,第一个字节代表重复的次数,第二个字节代表被重复的字符串。例如,(4,6)就代表字符串“6666”。但是,在JPEG编码中,RLC的含义就同其原有的意义略有不同。在JPEG编码中,假设RLC编码之后得到了一个(M,N)的数据对,其中M是两个非零AC系数之间连续的0的个数(即,行程长度),N是下一个非零的AC系数的值。采用这样的方式进行表示,是因为AC系数当中有大量的0,而采用Zigzag扫描也会使得AC系数中有很多连续的0的存在,如此一来,便非常适合于用RLC进行编码。

例如,现有一个字符串,如下所示:

57,45,0,0,0,0,23,0,-30,-8,0,0,1,000.....

经过RLC之后,将呈现出以下的形式:

(0,57) ; (0,45) ; (4,23) ; (1,-30) ; (0,-8) ; (2,1) ; (0,0)

注意,如果AC系数之间连续0的个数超过16,则用一个扩展字节(15,0)来表示16连续的0

3AC系数的中间格式

        根据前面提到的VLI表格,对于前面的字符串:

    (0,57) ; (0,45) ; (4,23) ; (1,-30) ; (0,-8) ; (2,1) ; (0,0)

只处理每对数右边的那个数据,对其进行VLI编码查找上面的VLI编码表格,可以发现,57在第6组当中,因此,可以将其写成(0,6),57的形式,该形式,称之为AC系数的中间格式。

同样的(0,45)的中间格式为:(0,6),45

 (1,-30)的中间格式为:(1,5),-30

4、熵编码

        在得到DC系数的中间格式和AC系数的中间格式之后,为进一步压缩图象数据,有必要对两者进行熵编码。JPEG标准具体规定了两种熵编码方式:Huffman编码和算术编码。JPEG基本系统规定采用Huffman编码(因为不存在专利问题),但JPEG标准并没有限制JPEG算法必须用Huffman编码方式或者算术编码方式。 

Huffman编码:对出现概率大的字符分配字符长度较短的二进制编码,对出现概率小的字符分配字符长度较长的二进制编码,从而使得字符的平均编码长度最短。Huffman编码的原理请参考数据结构中的Huffman树或者最优二叉树。

Huffman编码时DC系数与AC系数分别采用不同的Huffman编码表,对于亮度和色度也采用不同的Huffman编码表。因此,需要4Huffman编码表才能完成熵编码的工作。具体的Huffman编码采用查表的方式来高效地完成。然而,在JPEG标准中没有定义缺省的Huffman表,用户可以根据实际应用自由选择,也可以使用JPEG标准推荐的Huffman表。或者预先定义一个通用的Huffman表,也可以针对一副特定的图像,在压缩编码前通过搜集其统计特征来计算Huffman表的值。

下面我们举例来说明8*8图像子块经过DCT及量化之后的处理过程:

假设一个图像块经过量化以后得到以下的系数矩阵:

15 0 -1 0 0 0 0 0
-2 -1 0 0 0 0 0 0
-1 -1 0 0 0 0 0 0
0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0

显然,DC系数为15,假设前一个8*8的图像块的DC系数量化值为12,则当前DC系统同上一个DC系数之间的差值为3,通过查找VLI编码表,可以得到DC系数的中间格式为(2)(3),这里的2代表后面的数字(3)的编码长度为2位;之后,通过Zigzag扫描之后,遇到第一个非0AC系数为-2,遇到0的个数为1AC系数经过RLC编码后可表示为(1-2),通过查找VLI表发现,-2在第2组,因此,该AC系数的中间格式为(1,2-2
    
其余的点类似,可以求得这个8*8子块熵编码的中间格式为
DC)(2)(3);AC12)(-2),(01)(-1),(01)(-1),(01)(-1),(21)(-1),(EOB)(00
    
对于DC系数的中间格式(2)(3)而言,数字2DC亮度Huffman表得到011,数字3通过查找VLI编码表得到其被编码为11
    
对于AC系数的中间格式(1,2)(-2)而言,(1,2)AC亮度Huffman表得到11011-2通过查找VLI编码表得到其被编码为01

对于AC系数的中间格式(0,1)(-1)而言,(0,1)AC亮度Huffman表得到00,数字-1通过查找VLI编码表得到其被编码为0

对于AC系数的中间格式(2,1)(1)而言,(2,1)查AC亮度Huffman表得到11100,数字-1通过查找VLI编码表得到其被编码为0

对于AC系数的中间格式(0,0)而言,查AC亮度Huffman表得到1010
    
因此,最后这个8*8子块亮度信息压缩后的数据流为0111111011010000000001110001010。总共31比特,其压缩比是64*8/31=16.5,大约每个像素用半个比特。

5DCAC亮度Huffman


0 0