JPEG图像的编解码实现
基于Blackfin561的JPEG2000 压缩算法实现及优化

基于Blackfin561 的JPEG2000 压缩算法实现及优化O 引言JPEG2000 数字图像压缩标准是国际标准组织(ISO)和国际电信联盟(ITU)联合制定的新一代静止图像压缩标准。
与以往的压缩标准相比,JPEG2000 标准具有很多优点。
它不仅仅在图像编码过程中能保证良好的图像质量,而且还具有现代图像压缩所要求的新性能,如同时支持有损压缩和无损压缩两种模式、保证在图像传输过程中的容错性、支持感兴趣区域编码等。
但是,由于新技术的引入,JPEG2000 的算法复杂度也相应提高,在实际应用中,JPEG2000 并不如想象中的那么应用广泛。
而DSP 由于其丰富灵活的指令集、特殊的内部结构、超强的数据吞吐能力及运算速度,使得以DSP 处理器为核心的方法成为实现JPEG2000 算法的一种有效途径。
1 JPEG2000 系统的组成原理JPEG2000 相对于JPEG 的最大改进就是以离散小波变换(DWT)代替了DCT 编码。
JPEG2000 的编解码流程如图1 所示。
本系统首先对源图像数据进行离散小波变换,然后对变换后的小波系数进行量化,接着对量化后的数据熵编码,最后形成输出码流。
解码器是编码器的逆过程,解码时,首先对码流进行熵解码,然后解量化和小波反变换,最后生成重建图像数据。
通过预处理可为不同类型的图像提供一个统一的接口,以便于后续使用同样的编码器进行处理,这一步骤是将多种类型的图像压缩加入到统一框架中的关键。
它主要包括三个步骤:图像分片、直流平移和分量变换。
小波的多分辨率分析特性使之既可高效地描述图像的平坦区域,又可有效地表示图像信号的局部突变(即图像的边缘轮廓部分),它在空域和频域都有良好的局部性,因而能够聚焦到图像的任意细节。
优化截断嵌入块编码(The Embedded BlockCoding with Optimized Truncation,简称EBCOT)是JPEG2000 标准的核心,。
JPEG图像格式详解

JPEG图像格式详解JPEG压缩简介-------------1.色彩模型JPEG的图片使用的是YCrCb颜色模型,而不是计算机上最常用的RGB.关于色彩模型,这里不多阐述.只是说明,YCrCb模型更适合图形压缩.因为人眼对图片上的亮度Y的变化远比色度C的变化敏感.我们完全可以每个点保存一个8bit的亮度值,每2x2个点保存一个Cr Cb值,而图象在肉眼中的感觉不会起太大的变化.所以,原来用RGB模型,4个点需要4x3=12字节.而现在仅需要4+2=6字节;平均每个点占12bit.当然JPEG格式里允许每个点的C值都记录下来;不过MPEG里都是按12bit一个点来存放的,我们简写为YUV12.[R G B]->[Y Cb Cr]转换-------------------------(R,G,B都是8bit unsigned)|Y||0.2990.5870.114||R||0||Cb|=|-0.1687-0.33130.5|*|G|+|128||Cr||0.5-0.4187-0.0813||B||128|Y=0.299*R+0.587*G+0.114*B(亮度)Cb=-0.1687*R-0.3313*G+0.5*B+128Cr=0.5*R-0.4187*G-0.0813*B+128[Y,Cb,Cr]->[R,G,B]转换-------------------------R=Y+ 1.402*(Cr-128)G=Y-0.34414*(Cb-128)-0.71414*(Cr-128)B=Y+ 1.772*(Cb-128)一般,C值(包括Cb Cr)应该是一个有符号的数字,但这里被处理过了,方法是加上了128.JPEG里的数据都是无符号8bit的.2.DCT(离散余弦变换)JPEG里,要对数据压缩,先要做一次DCT变换.DCT变换的原理,涉及到数学知识,这里我们不必深究.反正和傅立叶变换(学过高数的都知道)是差不多了.经过个点为一个单位处理的.所以如果原始图片的长宽不是8的倍数,都需要先补成8的倍数,好一块块的处理.另外,记得刚才我说的Cr Cb都是2x2记录一次吗?所以大多数情况,是要补成16x16的整数块.按从左到右,从上到下的次序排列(和我们写字的次序一样).JPEG里是对Y Cr Cb分别做DCT变换的.这里进行DCT变换的Y,Cr,Cb值的范围都是-128~127.(Y被减去128)JPEG编码时使用的是Forward DCT(FDCT)解码时使用的Inverse DCT(IDCT)下面给出公式:FDCT:772*x+12*y+1F(u,v)=alpha(u)*alpha(v)*sum sum f(x,y)*cos(-------*u*PI)*cos(------*v*PI)x=0y=01616u,v=0,1,...,7{1/sqrt(8)(u==0)alpha(u)={{1/2(u!=0)IDCT:772*x+12*y+1f(x,y)=sum sum alpha(u)*alpha(v)*F(u,v)*cos(-------*u*PI)*cos(------*v*PI) u=0v=01616x,y=0,1 (7)这个步骤很花时间,另外有种AA&N优化算法,大家可以去inet自己找一下.在Intel主页上可以找到AA&N IDCT的MMX优化代码.(Intel主页上的代码,输入数据为12.4的定点数,输入矩阵需要转置90度)3.重排列DCT结果DCT将一个8x8的数组变换成另一个8x8的数组.但是内存里所有数据都是线形存放的,如果我们一行行的存放这64个数字,每行的结尾的点和下行开始的点就没有什么关系,所以JPEG规定按如下次序整理64个数字.0,1,5,6,14,15,27,28,2,4,7,13,16,26,29,42,3,8,12,17,25,30,41,43,9,11,18,24,31,40,44,53,10,19,23,32,39,45,52,54,20,22,33,38,46,51,55,60,35,36,48,49,57,58,62,63这样数列里的相邻点在图片上也是相邻的了.4.量化对于前面得到的64个空间频率振幅值,我们将对它们作幅度分层量化操作.方法就是分别除以量化表里对应值并四舍五入.for(i=0;i<=63;i++)vector[i]=(int)(vector[i]/quantization_table[i]+0.5)下面有张JPEG标准量化表.(按上面同样的弯曲次序排列)1611101624405161121214192658605514131624405769561417222951878062182237566810910377243555648110411392496478871031211201017292959811210010399这张表依据心理视觉阀制作,对8bit的亮度和色度的图象的处理效果不错.当然我们可以使用任意的量化表.量化表是定义在jpeg的DQT标记后.一般为Y值定义一个,为C值定义一个.量化表是控制JPEG压缩比的关键.这个步骤除掉了一些高频量,损失了很高细节.但事实上人眼对高空间频率远没有低频敏感.所以处理后的视觉损失很小.另一个重要原因是所有的图片的点与点之间会有一个色彩过渡的过程.大量的图象信息被包含在低空间频率中.经过量化处理后,在高空间频率段,将出现大量连续的零.注意,量化后的数据有可能超过2byte有符号整数的处理范围.5.0RLE编码现在我们矢量中有许多连续的0.我们可以使用RLE来压缩掉这些0.这里我们将跳过第一个矢量(后面将解释为什么)因为它的编码比较特别.假设有一组矢量(64个的后63个)是57,45,0,0,0,0,23,0,-30,-16,0,0,1,0,0,0,0,0,0,0,..,0经过RLE压缩后就是(0,57);(0,45);(4,23);(1,-30);(0,-16);(2,1);EOBEOB是一个结束标记,表示后面都是0了.实际上,我们用(0,0)表示EOB但是,如果这组数字不以0结束,那么就不需要EOB.另外需要注意的是,由于后面huffman编码的要求,每组数字前一个表示0的数量的必须是4bit,就是说,只能是0~15,所以,如果有这么一组数字:我们实际这样编码:(0,57);(15,0)(2,3);(4,2);(15,0)(15,0)(1,895),(0,0)注意(15,0)表示了16个连续的0.6.huffman编码为了提高储存效率,JPEG里并不直接保存数值,而是将数值按位数分成16组:数值组实际保存值00--1,110,1-3,-2,2,3200,01,10,11-7,-6,-5,-4,4,5,6,73000,001,010,011,100,101,110,111 -15,..,-8,8,..,1540000,..,0111,1000,..,1111-31,..,-16,16,..,31500000,..,01111,10000,..,11111-63,..,-32,32,..,636.-127,..,-64,64,..,1277.-255,..,-128,128,..,2558.-511,..,-256,256,..,5119.-1023,..,-512,512,..,102310.-2047,..,-1024,1024,..,204711.-4095,..,-2048,2048,..,409512.-8191,..,-4096,4096,..,819113.-16383,..,-8192,8192,..,1638314.-32767,..,-16384,16384,..,3276715.还是来看前面的例子:(0,57);(0,45);(4,23);(1,-30);(0,-8);(2,1);(0,0)只处理每对数右边的那个:57是第6组的,实际保存值为111001,所以被编码为(6,111001)45,同样的操作,编码为(6,101101)23->(5,10111)-30->(5,00001)-8->(4,0111)1->(1,1)前面的那串数字就变成了:(0,6),111001;(0,6),101101;(4,5),10111;(1,5),00001;(0,4),0111;(2,1),1;(0,0)括号里的数值正好合成一个字节.后面被编码的数字表示范围是-32767..32767.合成的字节里,高4位是前续0的个数,低4位描述了后面数字的位数.继续刚才的例子,如果06的huffman编码为111000(06对应111000为查表所得.对应成1~16bits的不定长数值.出现频率高的数字小于8bits,频率低的大于8bits,从而使整个的数据长度降低,关于huffman压缩算法,请查阅相关资料)69=(4,5)---1111111110011001(注:69=4*16+5=0x45)21=(1,5)---111111101104=(0,4)---101133=(2,1)---110110=EOB=(0,0)---1010那么最后对于前面的例子表示的63个系数(记得我们将第一个跳过了吗?)按位流写入JPG文件中就是这样的: 1110001110011110001011011111111110011001101111111111011000001 1011011111011110107.DC的编码-----------记得刚才我们跳过了每组64个数据的第一个吧,DC就是指的这个数字(后面63个简称AC)代入前面的FDCT公式可以得到c(0,0)77DC=F(0,0)=---------*sum sum f(x,y)*cos0*cos0其中c(0,0)=1/24x=0y=0177=---*sum sum f(x,y)8x=0y=0即一块图象样本的平均值.就是说,它包含了原始8x8图象块里的很多能量.(通常会得到一个很大的数值)JPEG的作者指出连续块的DC率之间有很紧密的联系,因此他们决定对8x8块的DC值的差别进行编码.(Y,Cb,Cr分别有自己的DC)Diff=DC(i)-DC(i-1)所以这一块的DC(i)就是:DC(i)=DC(i-1)+DiffJPG从0开始对DC编码,所以DC(0)=0.然后再将当前Diff值加在上一个值上得到当前值.下面再来看看上面那个例子:(记住我们保存的DC是和上一块DC的差值Diff)例如上面例子中,Diff是-511,就编码成如果9的Huffman编码是1111110(在JPG文件中,一般有两个Huffman表,一个是DC用,一个是AC用)那么在JPG文件中,DC的2进制表示为1111110000000000它将放在63个AC的前面,上面上个例子的最终BIT流如下:1111110000000000111000111001111000101101111111111001100110111 1111111011000001101101111101111010解码过程简述-------------8.一个数据单元Y的解码(其余类同)--------------------------------在整个图片解码的开始,你需要先初始化DC值为0.1)先解码DC:a)取得一个Huffman码(使用Huffman DC表)b)Huffman解码,看看后面的数据位数Nc)取得N位,计算Diff值d)DC+=Diffe)写入DC值:"vector[0]=DC"2)解码63个AC:-------循环处理每个AC直到EOB或者处理到64个ACa)取得一个Huffman码(使用Huffman AC表)b)Huffman解码,得到(前面0数量,组号)[记住:如果是(0,0)就是EOB了]c)取得N位(组号)计算ACd)写入相应数量的0e)接下来写入AC-----------------下一步的解码------------上一步我们得到了64个矢量.下面我们还需要做一些解码工作:2)重排列64个矢量到8x8的块中3)对8x8的块作IDCT对8x8块的(Y,Cb,Cr)重复上面的操作[Huffman解码,步骤1),2),3)]4)将所有的8bit数加上1285)转换YCbCr到RGB9.JPG文件(Byte级)里怎样组织图片信息-----------------------------------注意JPEG/JFIF文件格式使用Motorola格式,而不是Intel格式,就是说,如果是一个字的话,高字节在前,低字节在后.JPG文件是由一个个段(segments)构成的.每个段长度<=65535.每个段从一个标记字开始.标记字都是0xff打头的,以非0字节和0xFF结束.例如'FFDA','FFC4','FFC0'.每个标记有它特定意义,这是由第2字节指明的.例如,SOS(Start Of Scan='FFDA')指明了你应该开始解码.另一个标记DQT(Define Quantization Table=0xFFDB)就是说它后面有64字节的quantization表在处理JPG文件时,如果你碰到一个0xFF,而它后面的字节不是0,并且这个字节没有意义.那么你遇到的0xFF字节必须被忽略.(一些JPG里,常用用0xFF做某些填充用途)如果你在做huffman编码时碰巧产生了一个0xFF,那么就用0xFF0x00代替.就是说在jpeg图形解码时碰到FF00就把它当作FF处理.另外在huffman编码区域结束时,碰到几个bit没有用的时候,应该用1去填充.然后后面跟FF.下面是几个重要的标记--------------------SOI=Start Of Image='FFD8'这个标记只在文件开始出现一次EOI=End Of Image='FFD9'JPG文件都以FFD9结束RSTi=FFDi(i=0..7)[RST0=FFD0,RST7=FFD7]=复位标记通常穿插在数据流里,我想是担心JPG解码出问题吧(应该配合DRI使用).RST将Huffman的解码数据流复位.DC也重新从0开始计(SOS---RST0---RST1--RST2--......--RST6---RST7--RST0--...)10.标记-------下面是必须处理的标记SOF0=Start Of Frame0=FFC0SOS=Start Of Scan=FFDAAPP0=it's the marker used to identify a JPG file which uses the JFIF specification=FFE0COM=Comment=FFFEDNL=Define Number of Lines=FFDCDRI=Define Restart Interval=FFDDDQT=Define Quantization Table=FFDBDHT=Define Huffman Table=FFC411.JPG文件中Haffman表的储存-----------------------------JPEG里定义了一张表来描述Haffman树.定义在DHT标记后面.注意:Haffman代码的长度限制在16bit内.一般一个JPG文件里会有2类Haffman表:一个用于DC一个用于AC(实际有4个表,亮度的DC,AC两个,色度的DC,AC两个)这张表是这样保存的:1)16字节:第i字节表示了i位长的Huffman代码的个数(i=1到16)2)这表的长度(字节数)=这16个数字之和现在你可以想象这张表怎么存放的吧?对应字节就是对应Haffman代码等价数字.我不多解释,这需要你先了解Haffman算法.这里只举一个例子:Haffman表的表头是0,2,3,1,1,1,0,1,0,0,0,0,0,0,0,0就是说长度为1的代码没有长度为2的代码为0001长度为3的代码是100101110长度为4的代码是1110长度为5的代码是11110长度为6的代码是111110长度为7的代码没有(如果有一个的话应该是1111110)长度为8的代码是11111100.....如果表下面的数据是4557291723253428就是说45=0057=0129=10017=10123=110等等...如果你懂Haffman编码,这些不难理解12.采样系数-----------下面讲解的都是真彩JPG的解码,灰度JPG的解码很简单,因为图形中只有亮度信息.而彩色图形由(Y,Cr,Cb)构成,前面提到过,Y通常是每点采样一次,而Cr, Cb一般是2x2点采样一次,当然也有的JPG是逐点采样,或者每两点采样(横向两点,纵向一点)采样系数均被定义成对比最高采样系数的相对值.一般情况(即:Y逐点采样,Cr Cb每2x2点一次)下:Y有最高的采样率,横向采样系数HY=2纵向采样系数VY=2;Cb的横向采样系数HCb=1,纵向采样系数VCb=1;同样HCr=1,VCr=1在Jpeg里,8x8个原始数据,经过RLE,Huffman编码后的一串数据流称为一个Data Unit(DU)JPG里按DU为单位的编码次序如下:1)for(counter_y=1;counter_y<=VY;counter_y++)for(counter_x=1;counter_x<=HY;counter_x++){对Y的Data Unit编码}2)for(counter_y=1;counter_y<=VCb;counter_y++)for(counter_x=1;counter_x<=HCb;counter_x++){对Cb的Data Unit编码}3)for(counter_y=1;counter_y<=VCr;counter_y++)for(counter_x=1;counter_x<=HCr;counter_x++){对Cr的Data Unit编码}按我上面的例子:(HY=2,VY=2;HCb=VCb=1,HCr,VCr=1)就是这样一个次序YDU,YDU,YDU,YDU,CbDU,CrDU这些就描述了一块16x16的图形.16x16=(Hmax*8x Vmax*8)这里Hmax=HY=2一个(Hmax*8,Vmax*8)的块被称作MCU(Minimun Coded Unix)前面例子中一个MCU=YDU,YDU,YDU,YDU,CbDU,CrDU如果HY=1,VY=1HCb=1,VCb=1HCr=1,VCr=1这样(Hmax=1,Vmax=1),MCU只有8x8大,MCU=YDU,CbDU,CrDU对于灰度JPG,MCU只有一个DU(MCU=YDU)JPG文件里,图象的每个组成部分的采样系数定义在SOF0(FFC0)标记后13.简单说一下JPG文件的解码-------------------------解码程序先从JPG文件中读出采样系数,这样就知道了MCU的大小,算出整个图象有几个MCU.解码程序再循环逐个对MCU解码,一直到检查到EOI标记.对于每个MCU,按正规的次序解出每个DU,然后组合,转换成(R,G,B)就OK了附:JPEG文件格式~~~~~~~~~~~~~~~~-文件头(2bytes):$ff,$d8(SOI)(JPEG文件标识)-任意数量的段,见后面-文件结束(2bytes):$ff,$d9(EOI)段的格式:~~~~~~~~~-header(4bytes):$ff段标识n段的类型(1byte)sh,sl该段长度,包括这两个字节,但是不包括前面的$ff和n.注意:长度不是intel次序,而是Motorola的,高字节在前,低字节在后!-该段的内容,最多65533字节注意:-有一些无参数的段(下面那些前面注明星号的)这些段没有长度描述(而且没有内容),只有$ff和类型字节.-段之间无论有多少$ff都是合法的,必须被忽略掉.段的类型:*TEM=$01可以忽略掉SOF0=$c0帧开始(baseline JPEG),细节附后SOF1=$c1ditoSOF2=$c2通常不支持SOF3=$c3通常不支持SOF5=$c5通常不支持SOF6=$c6通常不支持SOF7=$c7通常不支持SOF9=$c9arithmetic编码(Huffman的一种扩展算法),通常不支持SOF10=$ca通常不支持SOF11=$cb通常不支持SOF13=$cd通常不支持SOF14=$ce通常不支持SOF14=$ce通常不支持SOF15=$cf通常不支持DHT=$c4定义Huffman Table,细节附后JPG=$c8未定义/保留(引起解码错误)DAC=$cc定义Arithmetic Table,通常不支持*RST0=$d0RSTn用于resync,通常被忽略*RST1=$d1*RST2=$d2*RST3=$d3*RST4=$d4*RST5=$d5*RST6=$d6*RST7=$d7SOI=$d8图片开始EOI=$d9图片结束SOS=$da扫描行开始,细节附后DQT=$db定义Quantization Table,细节附后DNL=$dc通常不支持,忽略DRI=$dd定义重新开始间隔,细节附后DHP=$de忽略(跳过)EXP=$df忽略(跳过)APP0=$e0JFIF APP0segment marker(细节略)APP15=$ef忽略JPG0=$f0忽略(跳过)JPG13=$fd忽略(跳过)COM=$fe注释,细节附后其它的段类型都保留必须跳过SOF0:Start Of Frame0:~~~~~~~~~~~~~~~~~~~~~~~-$ff,$c0(SOF0)-长度(高字节,低字节),8+components*3-数据精度(1byte)每个样本位数,通常是8(大多数软件不支持12和16) -图片高度(高字节,低字节),如果不支持DNL就必须>0-图片宽度(高字节,低字节),如果不支持DNL就必须>0-components数量(1byte),灰度图是1,YCbCr/YIQ彩色图是3,CMYK彩色图是4-每个component:3bytes-component id(1=Y,2=Cb,3=Cr,4=I,5=Q)-采样系数(bit0-3vert.,4-7hor.)-quantization table号DRI:Define Restart Interval:~~~~~~~~~~~~~~~~~~~~~~~~~~~~~-$ff,$dd(DRI)-长度(高字节,低字节),必须是4-MCU块的单元中的重新开始间隔(高字节,低字节),意思是说,每n个MCU块就有一个RSTn标记.第一个标记是RST0,然后是RST1等,RST7后再从RST0重复DQT:Define Quantization Table:~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~-$ff,$db(DQT)-长度(高字节,低字节)-QT信息(1byte):bit0..3:QT号(0..3,否则错误)bit 4..7:QT精度,0=8bit,否则16bit-n字节的QT,n=64*(精度+1)备注:-一个单独的DQT段可以包含多个QT,每个都有自己的信息字节-当精度=1(16bit),每个字都是高位在前低位在后DAC:Define Arithmetic Table:~~~~~~~~~~~~~~~~~~~~~~~~~~~~~法律原因,现在的软件不支持arithmetic编码.不能生产使用arithmetic编码的JPEG文件DHT:Define Huffman Table:~~~~~~~~~~~~~~~~~~~~~~~~~~-$ff,$c4(DHT)-长度(高字节,低字节)-HT信息(1byte):bit0..3:HT号(0..3,否则错误)bit4:HT类型,0=DC table,1=AC tablebit 5..7:必须是0-16bytes:长度是 1..16代码的符号数.这16个数的和应该<=256 -n bytes:一个包含了按递增次序代码长度排列的符号表(n=代码总数)备注:-一个单独的DHT段可以包含多个HT,每个都有自己的信息字节COM:注释:~~~~~~~~~~-$ff,$fe(COM)-注释长度(高字节,低字节)=L+2-注释为长度为L的字符流SOS:Start Of Scan:~~~~~~~~~~~~~~~~~~~-$ff,$da(SOS)-长度(高字节,低字节),必须是6+2*(扫描行内组件的数量)-扫描行内组件的数量(1byte),必须>=1,<=4(否则是错的)通常是3 -每个组件:2bytes-component id(1=Y,2=Cb,3=Cr,4=I,5=Q),见SOF0-使用的Huffman表:-bit0..3:AC table(0..3)-bit 4..7:DC table(0..3)-忽略3bytes(???)备注:-图片数据(一个个扫描行)紧接着SOS段.。
JPEG2000是新一代静止图像压缩国际标准

JPEG2000是新一代静止图像压缩国际标准,具有优越的图像压缩性能和高的图像质量,不仅克服了传统J PEG静止图像压缩标准在高压缩时出现方块效应的缺点,还提供了图像渐进传输、图像质量可伸缩及感兴趣区域编码等特性,可以应用于数码相机、医疗图像、网络传输等方面。
2 JPEG2000标准基本原理2.1 JPEG2000编解码框架JPEG2000编码器编码主要有预处理、小波变换、量化和熵编码等步骤,相对于编码过程,该系统的解码过程比较简单[1]。
JPEG2000编解码器框图如图1和图2所示。
图1 JPEG2000编码器框图图2 JPEG2000解码器框图2.2 JPEG2000编码的核心算法1)DWT变换通过离散小波变换多级小波分解,小波系数既能表示图像片中局部区域的高频信息也能表示图像片中的低频信息。
这样,即使在低比特率的情况下,也能保持较多的图像细节,另外,下一级分解得到的系数所表示图像在水平和垂直方向的分辨率只有上一级小波系数所表示的图像的一半,所以通过对图像的不同级进行解码,就可以得到具有不同空间分辨率的图像。
2)EBCOT算法EBCOT算法的基本思想是将小波变换以后的子带划分为大小固定的码块,对码块系数量化,按照二进制位分层的方法,从高有效位平面开始,依次对每个位平面上的所有小波系数位进行三个通道扫描建模(重要性传播编码通道、幅度精炼编码通道、清除编码通道),即位平面编码,生成上下文和0、1符号对,然后对这些上下文和符号对进行上下文算术编码,形成码块码流,完成第一阶段编码块编码;最后根据一定参数指标如码率、失真度,按率失真最优原则在每个独立码块码流中截取合适的位流组装成最终的图像压缩码流,完成第二阶段码流组装过程[2]。
2.3 EBCOT算法中块编码算法的改进研究及实现在JPEG2000编解码系统中,EBCOT算法是其重要的组成部分。
而EBCOT算法中的第一阶段块编码又是整个算法的核心,它占用了大量的编码时间,无论是无损压缩还是有损压缩,EBCOT算法中的位平面编码时间都占到整个编码耗时的50%以上[3][4]。
ImageSharp源码详解之JPEG编码原理(1)JPEG介绍

ImageSharp源码详解之JPEG编码原理(1)JPEG介绍最近在看GitHub上的⼀个很⽕的项⽬是:。
这是⼀个纯.net core的图像处理库,没有使⽤其他的任何依赖。
在看这个项⽬过程中激发了我对图像⽂件编码解码的兴趣。
于是从最简单的BMP图像开始看,到GIF格式卡了⼀段时间(主要卡在lzw编码过程和数据块中),到最后的JPEG格式(PNG格式不打算看了),经历了半个⽉时间才梳理出个⼤概。
趁着这个热乎劲,我想写下关于JPEG格式的系列⽂章,⽂章⽬录暂定如下:ImageSharp源码详解之JPEG压缩原理(4)量化ImageSharp源码详解之JPEG压缩原理(6)C#源码解析及调试技巧1.JPEG介绍JPEG(Joint Photographic Experts Group)是联合图像专家⼩组的英⽂缩写。
它由国际电话与电报咨询委员会CCITT(The International Telegraph and Telephone Consultative Committee)与国际标准化组织ISO于1986年联合成⽴的⼀个⼩组,负责制定静态数字图像的编码标准。
⼩组⼀直致⼒于标准化⼯作,开发研制出连续⾊调、多级灰度、静⽌图像的数字图像压缩编码⽅法,即JPEG算法。
JPEG算法被确定为国际通⽤标准,其适⽤范围⼴泛,除⽤于静态图像编码外,还推⼴到电视图像序列的帧内图像压缩。
⽽⽤JPEG算法压缩出来的静态图⽚⽂件称为JPEG⽂件,扩展名通常为*.jpg、*.jpe*.jpeg。
JPEG专家组开发了两种基本的压缩算法、两种数据编码⽅法、四种编码模式。
具体如下:压缩算法:1有损的离散余弦变换(Discrete Cosine Transform,DCT);2 ⽆损的预测技术压缩。
数据编码⽅法:1哈夫曼编码;2算术编码;编码模式:1基于DCT顺序模式:编/解码通过⼀次扫描完成;2基于DCT递进模式:编/解码需要多次扫描完成,扫描效果从粗糙到精细,逐级递进;3⽆损模式:基于DPCM,保证解码后完全精确恢复到原图像采样值;4层次模式:图像在多个空间多种分辨率进⾏编码,可以根据需要只对低分辨率数据作解码,放弃⾼分辨率信息。
JPEG图像解码方案

图形图像
吴嘉 慧
( 中山大 学信 息科学 与技 术学 院计算 机系 , 广州 5 0 0 ) 10 6
摘 要 : P G 文件是 当前 网络 最为流 行的 图像 文件格 式 , 有 高压 缩 比、 JE 具 多种 质量 选择 等特征 。 从 解码 角度详 细分析 J E P G压 缩算法 , } 而j 常规 的从 编码 的角度 , 出实践过程 中遇到 的 给 问题和 解决 方法。 关 键词 : P G 解码 ;图像 压缩 算 法 ; 程编 码 ;离散 余 弦 变换 ; 夫 曼编码 JE 行 哈
本文从解码 角度详 细分析 J E P G压缩算法 。 并且给 出实践过程中遇到 的问题和解决方法 ,展示一 个宏 观 的 JE P G数据组织 方式 。 列举 一些解码 中的细节 事项 。
1 解码过程 的概 述
JE P G图像文 件解码步 骤大概 如下 :
现 代 2 读 入文件 的相关信 息 计 按 照 JE P G文 件 数据存 储 方式 , 把要 解码 的文 件 算 的相关信 息读 出。 考方法是 设计 一 系列 的结 构体 对 机 参
引 言
] E JitP oorp i xet G op 是 联 合 P G(on h tga hcE p r ru ) s
图像 数据解 码 过程之用 。 ●从 图像 数 据流读 取一个 最小 编码 单元 ( U) MC , 并提 取 出里 边 的各个颜 色分 量单元 。 于如何 从数据 关
第Hale Waihona Puke 二 了 图像 的版 本 、 宽 、 样 因子 、 化表 、 长 采 量 哈夫 曼 表 等 重要信息 。所 以解码 前必须 将文 件头信 息 读出 , 以备
五 在标 记段 D T内 ,包 含 了一个 或者 多个 的哈 夫 五 H ( 理论说 明 1 )
JPEG图像格式详解

JPEG图像格式详解JPEG图像格式详解JPEG压缩简介-------------1.色彩模型JPEG的图片使用的是YCrCb颜色模型,而不是计算机上最常用的RGB.关于色彩模型,这里不多阐述.只是说明,YCrCb模型更适合图形压缩.因为人眼对图片上的亮度Y的变化远比色度C的变化敏感.我们完全可以每个点保存一个8bit的亮度值,每2x2个点保存一个Cr Cb值,而图象在肉眼中的感觉不会起太大的变化.所以,原来用RGB模型,4个点需要4x3=12字节.而现在仅需要4+2=6字节;平均每个点占12bit.当然JPEG格式里允许每个点的C值都记录下来;不过MPEG里都是按12bit一个点来存放的,我们简写为YUV12.[R G B]->[Y Cb Cr]转换-------------------------(R,G,B都是8bit unsigned)|Y||0.2990.5870.114||R||0||Cb|=|-0.1687-0.33130.5|*|G|+|128||Cr||0.5-0.4187-0.0813||B||128|Y=0.299*R+0.587*G+0.114*B(亮度)Cb=-0.1687*R-0.3313*G+0.5*B+128Cr=0.5*R-0.4187*G-0.0813*B+128[Y,Cb,Cr]->[R,G,B]转换-------------------------R=Y+ 1.402*(Cr-128)G=Y-0.34414*(Cb-128)-0.71414*(Cr-128)B=Y+ 1.772*(Cb-128)一般,C值(包括Cb Cr)应该是一个有符号的数字,但这里被处理过了,方法是加上了128.JPEG里的数据都是无符号8bit的.2.DCT(离散余弦变换)JPEG里,要对数据压缩,先要做一次DCT变换.DCT变换的原理,涉及到数学知识,这里我们不必深究.反正和傅立叶变换(学过高数的都知道)是差不多了.经过个点为一个单位处理的.所以如果原始图片的长宽不是8的倍数,都需要先补成8的倍数,好一块块的处理.另外,记得刚才我说的Cr Cb都是2x2记录一次吗?所以大多数情况,是要补成16x16的整数块.按从左到右,从上到下的次序排列(和我们写字的次序一样).JPEG里是对Y Cr Cb分别做DCT变换的.这里进行DCT变换的Y,Cr,Cb值的范围都是-128~127.(Y被减去128)JPEG编码时使用的是Forward DCT(FDCT)解码时使用的Inverse DCT(IDCT)下面给出公式:FDCT:772*x+12*y+1F(u,v)=alpha(u)*alpha(v)*sum sum f(x,y)*cos(-------*u*PI)*cos(------*v*PI)x=0y=01616u,v=0,1,...,7{1/sqrt(8)(u==0)alpha(u)={{1/2(u!=0)IDCT:772*x+12*y+1f(x,y)=sum sum alpha(u)*alpha(v)*F(u,v)*cos(-------*u*PI)*cos(------*v*PI) u=0v=01616x,y=0,1 (7)这个步骤很花时间,另外有种AA&N优化算法,大家可以去inet自己找一下.在Intel主页上可以找到AA&N IDCT的MMX优化代码.(Intel主页上的代码,输入数据为12.4的定点数,输入矩阵需要转置90度)3.重排列DCT结果DCT将一个8x8的数组变换成另一个8x8的数组.但是内存里所有数据都是线形存放的,如果我们一行行的存放这64个数字,每行的结尾的点和下行开始的点就没有什么关系,所以JPEG规定按如下次序整理64个数字.0,1,5,6,14,15,27,28,2,4,7,13,16,26,29,42,3,8,12,17,25,30,41,43,9,11,18,24,31,40,44,53,10,19,23,32,39,45,52,54,20,22,33,38,46,51,55,60,35,36,48,49,57,58,62,63这样数列里的相邻点在图片上也是相邻的了.4.量化对于前面得到的64个空间频率振幅值,我们将对它们作幅度分层量化操作.方法就是分别除以量化表里对应值并四舍五入.for(i=0;i<=63;i++)vector[i]=(int)(vector[i]/quantization_table[i]+0.5)下面有张JPEG标准量化表.(按上面同样的弯曲次序排列)1611101624405161121214192658605514131624405769561417222951878062182237566810910377243555648110411392496478871031211201017292959811210010399这张表依据心理视觉阀制作,对8bit的亮度和色度的图象的处理效果不错.当然我们可以使用任意的量化表.量化表是定义在jpeg的DQT标记后.一般为Y值定义一个,为C值定义一个.量化表是控制JPEG压缩比的关键.这个步骤除掉了一些高频量,损失了很高细节.但事实上人眼对高空间频率远没有低频敏感.所以处理后的视觉损失很小.另一个重要原因是所有的图片的点与点之间会有一个色彩过渡的过程.大量的图象信息被包含在低空间频率中.经过量化处理后,在高空间频率段,将出现大量连续的零.注意,量化后的数据有可能超过2byte有符号整数的处理范围.5.0RLE编码现在我们矢量中有许多连续的0.我们可以使用RLE来压缩掉这些0.这里我们将跳过第一个矢量(后面将解释为什么)因为它的编码比较特别.假设有一组矢量(64个的后63个)是57,45,0,0,0,0,23,0,-30,-16,0,0,1,0,0,0,0,0,0,0,..,0经过RLE压缩后就是(0,57);(0,45);(4,23);(1,-30);(0,-16);(2,1);EOBEOB是一个结束标记,表示后面都是0了.实际上,我们用(0,0)表示EOB但是,如果这组数字不以0结束,那么就不需要EOB.另外需要注意的是,由于后面huffman编码的要求,每组数字前一个表示0的数量的必须是4bit,就是说,只能是0~15,所以,如果有这么一组数字:我们实际这样编码:(0,57);(15,0)(2,3);(4,2);(15,0)(15,0)(1,895),(0,0)注意(15,0)表示了16个连续的0.6.huffman编码为了提高储存效率,JPEG里并不直接保存数值,而是将数值按位数分成16组:数值组实际保存值00--1,110,1-3,-2,2,3200,01,10,11-7,-6,-5,-4,4,5,6,73000,001,010,011,100,101,110,111 -15,..,-8,8,..,1540000,..,0111,1000,..,1111-31,..,-16,16,..,31500000,..,01111,10000,..,11111-63,..,-32,32,..,636.-127,..,-64,64,..,1277.-255,..,-128,128,..,2558.-511,..,-256,256,..,5119.-1023,..,-512,512,..,102310.-2047,..,-1024,1024,..,204711.-4095,..,-2048,2048,..,409512.-8191,..,-4096,4096,..,819113.-16383,..,-8192,8192,..,1638314.-32767,..,-16384,16384,..,3276715.还是来看前面的例子:(0,57);(0,45);(4,23);(1,-30);(0,-8);(2,1);(0,0)只处理每对数右边的那个:57是第6组的,实际保存值为111001,所以被编码为(6,111001) 45,同样的操作,编码为(6,101101)23->(5,10111)-30->(5,00001)-8->(4,0111)1->(1,1)前面的那串数字就变成了:(0,6),111001;(0,6),101101;(4,5),10111;(1,5),00001;(0,4),0111;(2,1),1;(0,0)括号里的数值正好合成一个字节.后面被编码的数字表示范围是-32767..32767.合成的字节里,高4位是前续0的个数,低4位描述了后面数字的位数.继续刚才的例子,如果06的huffman编码为111000(06对应111000为查表所得.对应成1~16bits的不定长数值.出现频率高的数字小于8bits,频率低的大于8bits,从而使整个的数据长度降低,关于huffman压缩算法,请查阅相关资料)69=(4,5)---1111111110011001(注:69=4*16+5=0x45)21=(1,5)---111111101104=(0,4)---101133=(2,1)---110110=EOB=(0,0)---1010那么最后对于前面的例子表示的63个系数(记得我们将第一个跳过了吗?)按位流写入JPG文件中就是这样的: 1110001110011110001011011111111110011001101111111111 011000001 1011011111011110107.DC的编码-----------记得刚才我们跳过了每组64个数据的第一个吧,DC就是指的这个数字(后面63个简称AC)代入前面的FDCT公式可以得到c(0,0)77DC=F(0,0)=---------*sum sum f(x,y)*cos0*cos0其中c(0,0)=1/24x=0y=0177=---*sum sum f(x,y)8x=0y=0即一块图象样本的平均值.就是说,它包含了原始8x8图象块里的很多能量.(通常会得到一个很大的数值)JPEG的作者指出连续块的DC率之间有很紧密的联系,因此他们决定对8x8块的DC值的差别进行编码.(Y,Cb,Cr分别有自己的DC)Diff=DC(i)-DC(i-1)所以这一块的DC(i)就是:DC(i)=DC(i-1)+DiffJPG从0开始对DC编码,所以DC(0)=0.然后再将当前Diff值加在上一个值上得到当前值.下面再来看看上面那个例子:(记住我们保存的DC是和上一块DC 的差值Diff)例如上面例子中,Diff是-511,就编码成如果9的Huffman编码是1111110(在JPG文件中,一般有两个Huffman表,一个是DC用,一个是AC用)那么在JPG文件中,DC的2进制表示为1111110000000000它将放在63个AC的前面,上面上个例子的最终BIT流如下:1111110000000000111000111001111000101101111111111 001100110111 1111111011000001101101111101111010 解码过程简述-------------8.一个数据单元Y的解码(其余类同)--------------------------------在整个图片解码的开始,你需要先初始化DC值为0.1)先解码DC:a)取得一个Huffman码(使用Huffman DC表)b)Huffman解码,看看后面的数据位数Nc)取得N位,计算Diff值d)DC+=Diffe)写入DC值:"vector[0]=DC"2)解码63个AC:-------循环处理每个AC直到EOB或者处理到64个ACa)取得一个Huffman码(使用Huffman AC表)b)Huffman解码,得到(前面0数量,组号)[记住:如果是(0,0)就是EOB了]c)取得N位(组号)计算ACd)写入相应数量的0e)接下来写入AC-----------------下一步的解码------------上一步我们得到了64个矢量.下面我们还需要做一些解码工作:2)重排列64个矢量到8x8的块中3)对8x8的块作IDCT对8x8块的(Y,Cb,Cr)重复上面的操作[Huffman解码,步骤1),2),3)]4)将所有的8bit数加上1285)转换YCbCr到RGB9.JPG文件(Byte级)里怎样组织图片信息-----------------------------------注意JPEG/JFIF文件格式使用Motorola格式,而不是Intel格式,就是说,如果是一个字的话,高字节在前,低字节在后.JPG文件是由一个个段(segments)构成的.每个段长度<=65535.每个段从一个标记字开始.标记字都是0xff打头的,以非0字节和0xFF 结束.例如'FFDA','FFC4','FFC0'.每个标记有它特定意义,这是由第2字节指明的.例如,SOS(Start Of Scan='FFDA')指明了你应该开始解码.另一个标记DQT(Define Quantization Table=0xFFDB)就是说它后面有64字节的quantization表在处理JPG文件时,如果你碰到一个0xFF,而它后面的字节不是0,并且这个字节没有意义.那么你遇到的0xFF字节必须被忽略.(一些JPG 里,常用用0xFF做某些填充用途)如果你在做huffman编码时碰巧产生了一个0xFF,那么就用0xFF0x00代替.就是说在jpeg图形解码时碰到FF00就把它当作FF处理.另外在huffman编码区域结束时,碰到几个bit没有用的时候,应该用1去填充.然后后面跟FF.下面是几个重要的标记--------------------SOI=Start Of Image='FFD8'这个标记只在文件开始出现一次EOI=End Of Image='FFD9'JPG文件都以FFD9结束RSTi=FFDi(i=0..7)[RST0=FFD0,RST7=FFD7]=复位标记通常穿插在数据流里,我想是担心JPG解码出问题吧(应该配合DRI 使用).RST将Huffman的解码数据流复位.DC也重新从0开始计(SOS---RST0---RST1--RST2--......--RST6---RST7--RST0--...)10.标记-------下面是必须处理的标记SOF0=Start Of Frame0=FFC0SOS=Start Of Scan=FFDAAPP0=it's the marker used to identify a JPG file which uses the JFIF specification=FFE0COM=Comment=FFFEDNL=Define Number of Lines=FFDCDRI=Define Restart Interval=FFDDDQT=Define Quantization Table=FFDBDHT=Define Huffman Table=FFC411.JPG文件中Haffman表的储存-----------------------------JPEG里定义了一张表来描述Haffman树.定义在DHT标记后面.注意:Haffman代码的长度限制在16bit内.一般一个JPG文件里会有2类Haffman表:一个用于DC一个用于AC(实际有4个表,亮度的DC,AC两个,色度的DC,AC两个) 这张表是这样保存的:1)16字节:第i字节表示了i位长的Huffman代码的个数(i=1到16)2)这表的长度(字节数)=这16个数字之和现在你可以想象这张表怎么存放的吧?对应字节就是对应Haffman 代码等价数字.我不多解释,这需要你先了解Haffman算法.这里只举一个例子:Haffman表的表头是0,2,3,1,1,1,0,1,0,0,0,0,0,0,0,0就是说长度为1的代码没有长度为2的代码为0001长度为3的代码是100101110长度为4的代码是1110长度为5的代码是11110长度为6的代码是111110长度为7的代码没有(如果有一个的话应该是1111110)长度为8的代码是11111100.....如果表下面的数据是4557291723253428就是说45=0057=0129=10017=10123=110等等...如果你懂Haffman编码,这些不难理解12.采样系数-----------下面讲解的都是真彩JPG的解码,灰度JPG的解码很简单,因为图形中只有亮度信息.而彩色图形由(Y,Cr,Cb)构成,前面提到过,Y通常是每点采样一次,而Cr, Cb一般是2x2点采样一次,当然也有的JPG是逐点采样,或者每两点采样(横向两点,纵向一点)采样系数均被定义成对比最高采样系数的相对值.一般情况(即:Y逐点采样,Cr Cb每2x2点一次)下:Y有最高的采样率,横向采样系数HY=2纵向采样系数VY=2;Cb的横向采样系数HCb=1,纵向采样系数VCb=1;同样HCr=1,VCr=1在Jpeg里,8x8个原始数据,经过RLE,Huffman编码后的一串数据流称为一个Data Unit(DU)JPG里按DU为单位的编码次序如下:1)for(counter_y=1;counter_y<=VY;counter_y++)for(counter_x=1;counter_x<=HY;counter_x++){对Y的Data Unit编码}2)for(counter_y=1;counter_y<=VCb;counter_y++)for(counter_x=1;counter_x<=HCb;counter_x++){对Cb的Data Unit编码}3)for(counter_y=1;counter_y<=VCr;counter_y++)for(counter_x=1;counter_x<=HCr;counter_x++){对Cr的Data Unit编码}按我上面的例子:(HY=2,VY=2;HCb=VCb=1,HCr,VCr=1)就是这样一个次序YDU,YDU,YDU,YDU,CbDU,CrDU这些就描述了一块16x16的图形.16x16=(Hmax*8x Vmax*8)这里Hmax=HY=2一个(Hmax*8,Vmax*8)的块被称作MCU(Minimun Coded Unix)前面例子中一个MCU=YDU,YDU,YDU,YDU,CbDU,CrDU 如果HY=1,VY=1HCb=1,VCb=1HCr=1,VCr=1这样(Hmax=1,Vmax=1),MCU只有8x8大,MCU=YDU,CbDU,CrDU对于灰度JPG,MCU只有一个DU(MCU=YDU)JPG文件里,图象的每个组成部分的采样系数定义在SOF0(FFC0)标记后13.简单说一下JPG文件的解码-------------------------解码程序先从JPG文件中读出采样系数,这样就知道了MCU的大小,算出整个图象有几个MCU.解码程序再循环逐个对MCU解码,一直到检查到EOI标记.对于每个MCU,按正规的次序解出每个DU,然后组合,转换成(R,G,B)就OK了附:JPEG文件格式~~~~~~~~~~~~~~~~-文件头(2bytes):$ff,$d8(SOI)(JPEG文件标识)-任意数量的段,见后面-文件结束(2bytes):$ff,$d9(EOI)段的格式:~~~~~~~~~-header(4bytes):$ff段标识n段的类型(1byte)sh,sl该段长度,包括这两个字节,但是不包括前面的$ff和n.注意:长度不是intel次序,而是Motorola的,高字节在前,低字节在后!-该段的内容,最多65533字节注意:-有一些无参数的段(下面那些前面注明星号的)这些段没有长度描述(而且没有内容),只有$ff和类型字节.-段之间无论有多少$ff都是合法的,必须被忽略掉.段的类型:*TEM=$01可以忽略掉SOF0=$c0帧开始(baseline JPEG),细节附后SOF1=$c1ditoSOF2=$c2通常不支持SOF3=$c3通常不支持SOF5=$c5通常不支持SOF6=$c6通常不支持SOF7=$c7通常不支持SOF9=$c9arithmetic编码(Huffman的一种扩展算法),通常不支持SOF10=$ca通常不支持SOF11=$cb通常不支持SOF13=$cd通常不支持SOF14=$ce通常不支持SOF14=$ce通常不支持SOF15=$cf通常不支持DHT=$c4定义Huffman Table,细节附后JPG=$c8未定义/保留(引起解码错误)DAC=$cc定义Arithmetic Table,通常不支持*RST0=$d0RSTn用于resync,通常被忽略*RST1=$d1*RST2=$d2*RST3=$d3*RST4=$d4*RST5=$d5*RST6=$d6*RST7=$d7SOI=$d8图片开始EOI=$d9图片结束SOS=$da扫描行开始,细节附后DQT=$db定义Quantization Table,细节附后DNL=$dc通常不支持,忽略DRI=$dd定义重新开始间隔,细节附后DHP=$de忽略(跳过)EXP=$df忽略(跳过)APP15=$ef忽略JPG0=$f0忽略(跳过)JPG13=$fd忽略(跳过)COM=$fe注释,细节附后其它的段类型都保留必须跳过SOF0:Start Of Frame0:~~~~~~~~~~~~~~~~~~~~~~~-$ff,$c0(SOF0)-长度(高字节,低字节),8+components*3-数据精度(1byte)每个样本位数,通常是8(大多数软件不支持12和16) -图片高度(高字节,低字节),如果不支持DNL就必须>0-图片宽度(高字节,低字节),如果不支持DNL就必须>0-components数量(1byte),灰度图是1,YCbCr/YIQ彩色图是3,CMYK彩色图是4-每个component:3bytes-component id(1=Y,2=Cb,3=Cr,4=I,5=Q)-采样系数(bit0-3vert.,4-7hor.)-quantization table号DRI:Define Restart Interval:~~~~~~~~~~~~~~~~~~~~~~~~~~~~~-$ff,$dd(DRI)-长度(高字节,低字节),必须是4-MCU块的单元中的重新开始间隔(高字节,低字节),意思是说,每n个MCU块就有一个RSTn标记.第一个标记是RST0,然后是RST1等,RST7后再从RST0重复DQT:Define Quantization Table:~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~-$ff,$db(DQT)-长度(高字节,低字节)-QT信息(1byte):bit0..3:QT号(0..3,否则错误)bit 4..7:QT精度,0=8bit,否则16bit-n字节的QT,n=64*(精度+1)备注:-当精度=1(16bit),每个字都是高位在前低位在后DAC:Define Arithmetic Table:~~~~~~~~~~~~~~~~~~~~~~~~~~~~~法律原因,现在的软件不支持arithmetic编码.不能生产使用arithmetic编码的JPEG文件DHT:Define Huffman Table:~~~~~~~~~~~~~~~~~~~~~~~~~~-$ff,$c4(DHT)-长度(高字节,低字节)-HT信息(1byte):bit0..3:HT号(0..3,否则错误)bit4:HT类型,0=DC table,1=AC tablebit 5..7:必须是0-16bytes:长度是1..16代码的符号数.这16个数的和应该<=256 -n bytes:一个包含了按递增次序代码长度排列的符号表(n=代码总数)备注:-一个单独的DHT段可以包含多个HT,每个都有自己的信息字节COM:注释:~~~~~~~~~~-$ff,$fe(COM)-注释长度(高字节,低字节)=L+2-注释为长度为L的字符流SOS:Start Of Scan:~~~~~~~~~~~~~~~~~~~-$ff,$da(SOS)-长度(高字节,低字节),必须是6+2*(扫描行内组件的数量)-扫描行内组件的数量(1byte),必须>=1,<=4(否则是错的)通常是3 -每个组件:2bytes-component id(1=Y,2=Cb,3=Cr,4=I,5=Q),见SOF0-使用的Huffman表:-bit0..3:AC table(0..3)-bit 4..7:DC table(0..3)-忽略3bytes()备注:-图片数据(一个个扫描行)紧接着SOS段.。
JPEG图像硬件解码低功耗设计

从 左 到 右 【。 l 1
为 实 时 通 信 系 统 的存 储 容 量 、 输 带 宽 和 功 耗 提 出 了 挑 传
战 。 在 医 疗遥
o t z d n r e t g t g o p w r i i ain P we c n u t n s p i z d r m a g rt m e e , a c i cu e e e a d pi e i od r o e a o d o e d s p t . o r o s mp i i mi s o o o t mie fo lo i lv l r h t t r lv l n h e cr u t l v l y t e ial .F n l i i e e s n h t l c c y i al t r u h h e e t n f a r l t e y o l t e t lt r mp e n h VL I f R L— e e y, h o g te r c i o e ai l c mp ee t s o v p a o f m we i l me t t e S o T l v l a d g t- e e i l t n h e u t h w d t a u c in me t t e d ma d n ae lv l smu ai .T e r s l s o e h t f n t e h e n . o s o
H f n编 码 后 代 码 的 长 度 不 一 致 , 如 果 解 码 器 用 uf ma
中 图 分 类 号 :T 9 9 8 N 1 .1 文 献 标 识 码 :A
L w - o r d sg f J EG r p i s h r wa e e o i g o p we e in o P g a h c a d r d c d n
图像编解码技术及应用

图像编解码技术及应用1. 什么是图像编解码技术?图像编解码技术(Image Encoding and Decoding)是指一系列将图像信号转换成数字信号的技术,也包括将数字信号还原成原始图像的技术。
图像编解码技术广泛应用于数字图像处理、数字图像传输和储存等领域,使得图像能够更加便捷地传输和存储。
常见的图像编解码技术包括JPEG、PNG、GIF等。
其中,JPEG是最常见的图像编解码技术之一,适用于不带透明度的复杂色彩图像。
PNG则适用于带透明度的复杂色彩图像,但其文件大小比JPEG大。
GIF则适用于简单色彩图像和动态图像。
2. 图像编解码技术的原理图像编解码技术的原理是将原始图像转化成数字信号,再传输或储存这些数字信号。
具体的过程包括以下几个步骤:1.采样和量化:将原始图像按照一定的采样率进行采样,并对采样到的数字信号进行量化,即将其转化为离散的数字。
2.编码:对采样和量化后的数字信号进行编码,将其转换为二进制码。
3.压缩:为了降低文件大小,图像编解码技术通常采用压缩技术对编码后的二进制码进行压缩。
4.解码:将压缩后的二进制码转化成编码前的二进制码。
5.重构:根据解码后的二进制码,重构出原始的图像。
3. 图像编解码技术的应用图像编解码技术在数字图像处理、数字图像传输和储存等领域中得到了广泛应用。
在数字图像处理领域,图像编解码技术可以用于图像的修改、增强和复原,例如对图像进行缩放、旋转和修复等操作。
在数字图像传输领域,图像编解码技术可以用于图像的网络传输和无线传输,例如在网络视频会议中传送视频图像,或者在移动设备间传送图像。
在数字图像储存领域,图像编解码技术可以降低图像文件的大小,从而节约储存空间和传输带宽。
例如,JPEG是最常用的图像储存格式之一。
4. 图像编解码技术的未来发展随着计算机技术和互联网技术的发展,图像编解码技术也在不断地发展和创新。
一方面,图像编解码技术的编码器和解码器都在不断地优化和改进,以提高图像编解码的效率和准确性,并能够处理更加复杂和高清晰度的图像。
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
毕业论文论文题目(中文)JPEG图像的编解码实现论文题目(外文)Encoding and decoding of JPEG image摘要JPEG是一种十分先进的图像压缩技术,它用有损压缩方式去除冗余的图像数据,在获得极高的压缩率的同时能展现十分丰富生动的图像。
本文设计和实现一个JPEG图像编解码器来进行图像转换,利用离散余弦变换、熵编码、Huffman编码等图像压缩技术将BMP图像转换成JPEG图像,即进行图像的压缩。
验证JPEG压缩编码算法的可行性。
通过比对图像压缩前后实际效果,探讨压缩比,峰值信噪比等评价图像数据压缩程度及压缩质量的关键参数,对JPEG 压缩编码算法的实用性和优越性进行研究。
关键词:JPEG;编码;解码;图像压缩AbstractJPEG is a very advanced image compression technology, it uses lossy compression to remove redundant image data, in obtaining a very high compression rate can show a very rich and vivid image. In this project, a JPEG image codec is designed and implemented to transform image, using discrete cosine transform, entropy coding, Huffman coding and other image compression techniques to convert BMP images into JPEG images. Verifies the feasibility of JPEG compression coding algorithm. Through the comparison of the actual effect of image compression, the key parameters of compression ratio, peak Snr, and the compression quality of image data are discussed, and the practicability and superiority of JPEG compression coding algorithm are researched.Key words: JPEG; encoding; decoding; image compression目录摘要.............................................................................................................................................................. I I Abstract.......................................................................................................................................................... III 目录............................................................................................................................................................ IV 第一章绪论. (1)第二章JPEG图像编码压缩原理 (3)第三章实验过程与结论 (11)致谢 (14)第一章 绪 论1.1 研究背景和意义在如今这个信息化社会里,计算机网络飞速发展,信息交流成为了人们生活中必不可少的部分,近年来随着自媒体的兴起,大量的信息更是充斥着人们的日常生活,而图像作为日常信息交流中最常用的信息传递媒介之一,充满着各个信息平台和设备终端。
随着生活节奏的加快,人们对信息交流的质量和速度也有着越来越高的要求,但是由于图像和视频本身的数据量非常大,给存储和传输带来了很多不便,尤其在网络中传递图形图像时对传输速度有着很高的要求,这就使得图像压缩和视频压缩成为网络技术中的基础性技术。
所以图像压缩和视频压缩得到了非常广泛的应用。
图像压缩是一种减少描绘一幅图像所需数据量的技术和科学,它是数字图像处理领域中最有用和商业上最成功的技术之一。
每天被压缩和解压缩的图像的数量是惊人的。
为了理解图像压缩的需要,考虑使用720×480×24比特像素阵列来描绘2小时的标准清晰度(SD )电视电影所需的数据量。
数字电影是由一帧一帧的全彩色静止图像排列起来而组成的,为了能让人眼感觉到流畅的视频画面,视频播放时必须以30帧每秒的速率连续地显示这些帧,因此必须以()30720480331104000/⨯⨯⨯=帧像素字节字节秒秒帧像素的速率读取SD 数字电影数据。
可以计算得2小时电影的数据量为()21131104000602 2.2410⨯⨯≈⨯字节秒小时字节秒小时假设用传统的12cm ,容量为8.5GB 双层光盘的话,这么多的数据需要27张才能存储完。
这很明显是不现实的,所以为了能把这部2小时的电影存放在单张光盘上,视频的每一帧应该以平均26.3的系数进行压缩。
除此之外,为了减少存储空间和传输时间,网页图像和高分辨率数字摄像机图片也需要进行数据压缩。
例如,利用宽带发送数据的速率为12Mbps (兆比特每秒)。
以该速率传输一幅128×128×24比特全彩色小图像需要的时间为0.03秒。
而经过压缩后再传输,这个时间可以减少2~10倍,甚至更多。
同理,考虑大小为1GB的闪存卡中可存储的8兆像素数字摄像机所拍摄的未压缩全彩色照片数量约为41幅(每幅约24MB),而经过压缩后,该数量也以2~10倍的数量增加。
除了这些应用外,图像压缩在视频会议、遥感、文本和医学图像处理、传真传输等诸多领域也扮演者重要的角色。
1.2 发展历史与现状JPEG的全称为Joint Photographic Experts Group(联合照片专家小组),它是一个在国际标准组织(ISO)下从事静态图像压缩标准制定的委员会。
它是CCITT 于1992年正式通过的用来处理连续色调静止图象的压缩标准。
JPEG既可以进行有损压缩,也可以进行无损压缩,最常见也最常用的就是有损压缩的方法,其压缩过程可分为颜色模式转换及采样、DCT变换、量化、编码等几部分。
联合照片专家小组制定出了第一套国标静态图像压缩标准:ISO 10918-1,也就是我们俗称的JPEG。
因为JPEG压缩编码拥有数据量小且兼容性好的优良品质,所以它在短短的几年内就获得了巨大的成功,目前网络媒体上大约百分之八十的图形图像都采用的是JPEG压缩标准。
也正是由于JPEG格式可以对扫描或自然图像进行大幅度的压缩,使它成为迅速显示图像并保存较好分辨率的理想格式,这样利于存储和传输,所以在Internet上得到了广泛的应用。
随后,在诸多媒体应用领域的大量激增下,原始JPEG压缩技术已经不能满足人们对多媒体图形图像资料的要求。
在此条件下,催生了更高压缩率以及更多新功能的新一代静态图像压缩技术——JPEG 2000。
JPEG 2000同样是由JPEG组织负责制定的,命名为“ISO 15444”。
该小组自1997年三月开始筹划,经过三年的艰苦努力,终于在2000年3月东京的一个会议上,提前出台了规定基本编码系统的最终协议草案。
这比人们预计2000年12月才能制定完成要早,没有出现人们担心的改名为JPEG2001的情况。
近年来,有关图像编码技术对的研究也成果百出,图像编码技术已经发展到一种很成熟的状态,人们开始突破了传统的信源编码理论,开发出了小波变换编码、分形理论、人工神经网络理论以及视觉仿真理论,这些编码技术的特点是:充分考虑了人的视觉特性,使用了人工神经元网络的压缩编码技术。
这些现代编码技术的出现与发展推动着图像编码技术走向繁荣。
1.3 课题研究目标和内容本课题对图像压缩编码的相关基础理论与技术进行学习研究,对BMP和JPEG两种图像文件格式也做针对性的理解和认识,在此基础上进行JPEG图像压缩编码算法的研究,结合实际情况,探索高效的JPEG图像编解码方法,从而在一定意义上实现图形的压缩编码和解码处理,程序采用C++环境,对图像压缩算法进行实现,并能做出一个可视化界面来处理图片,从而能更好地实现两种格式之间的转换,最后通过计算压缩比和峰值信噪比进行算法性能的分析比较。
本课题的研究内容包括:图形图像压缩编码原理技术,BMP、JPEG的图像格式,JPEG图像的压缩编码算法,C++编程环境实现图像处理,matlab工具计算峰值信噪比。
实现BMP和JPEG图像文件的相互转换,同时研究图像压缩处理算法,对图像处理的未来进行探讨与展望。
第二章JPEG图像编码压缩原理2.1 图像编码方法JPEG专家组研究和开发了两种基本的压缩算法、两种熵编码方法、四种编码模式来实现JPEG图像的编解码。
如下所示:压缩算法:(1)有损的离散余弦变换DCT(2)无损的预测压缩技术;熵编码方法:(1)Huffman编码;(2)算术编码;编码模式:(1)基于DCT的顺序模式:通过一次扫描完成编解码;(2)基于DCT的渐进模式:编码、解码需要经过多次扫描才能完成,扫描程度从粗略到精细,逐级递增;(3)无损模式:基于DPCM,这种方法保证解码后图像能完全并精确地恢复到原图采样值;(4)层次模式:图像编码在多个空间分辨率中进行,并可以选择放弃高分辨率信息,只对低分辨率数据做解码;由于在实际应用中JPEG 图像的编码算法大多使用的是离散余弦变换、Huffman 编码、顺序编码的模式,因此这样的方式也被人们称为JPEG 图像压缩的基本系统。
2.2 JPEG 压缩步骤JPEG 压缩是有信息损失的,它的基本原理是针对人的视角系统的某种特性,采用量化以及无损压缩编码相结合的方式,消除视角的冗余信息,并去掉数据本身的冗余信息。
如下所列的是JPEG 压缩编码算法的主要计算步骤:(1)色彩模式转换及采样(2)离散余弦变换(3)量化(4)Z 字形编排(5)直流系数编码(6)交流系数编码(7)熵编码具体过程如图3-1所示图 2-1 JPEG 的压缩过程2.3 JPEG 压缩编码原理2.3.1 色彩模式转换及采样YCrCb 颜色空间中,Y 代表亮度,Cr ,Cb 则代表色度和饱和度,有时也将Cb ,Cr 两者统称为色度,三者通常以Y ,U ,V 来表示,即用U 代表Cb ,用V 代表Cr 。