JPEG图像压缩解压算法——C++实现

来源:互联网 发布:访客统计系统源码 编辑:程序博客网 时间:2024/05/16 10:41

兹于2017年11月,应《多媒体技术基础》课程实验的要求,本人(惠州学院->信息科学技术学院->软件工程->戴文治)就基于JPEG图像压缩解压算法做了较为深入的理解,用C++语言实现JPEG图像压缩解压算法。



JPEG图像压缩解压算法


一、实验目的

1.掌握JPEG的压缩原理;

2.熟知FDCT变换方法;

3.掌握JPEG所采用的行程编码、霍夫曼编码、差分编码等压缩技术;

4.掌握JPEG解压原理。


二、实验设备与环境

Windows 7 操作系统,Dev-C ++,MATLAB


三、实验内容、程序清单及运行结果

实验要求:

根据书本P76-P83内容,用Dev-C ++编写JPEG压缩与解压算法。(没有《多媒体技术基础(第三版)》,可以在这里下载PDF电子书,也可在中国知网查阅类似文章如:《用查表法快速实现二维8×8离散余弦逆变换的研究——纪秀花 张彩明 韩慧健》和《基于JPEG标准的静态图像压缩算法研究——张元伟 刘彦隆》等)

1. 实现JPEG压缩编码程序。

2. 实现JPEG解压程序。


实验操作和步骤:

1.打开Dev-C ++,进入编程环境,新建一个源代码文件,文件名任意;

2.将下面我所编写的代码拷贝到所新建的源代码文件中;

3.点击编译运行。


算法简介:

该算法操作是把一个单独的彩色图像分量分成8×8的图像块,即是对源图像的一个分量样本分成8×8的数据,然后进行压缩编码和解码。


自创C++源代码

/***作者:戴文治*时间:2017年11月17日*描述:JPEG压缩与解压算法*测试环境:Dev-C++ 5.9.2*/暂时不放源码


测试用例(书本P83):

139 144 149 153 155 155 155 155

144 151 153 156 159 156 156 156

150 155 160 163 158 156 156 156

159 161 162 160 160 159 159 159

159 160 161 162 162 155 155 155

161 161 161 161 160 157 157 157

162 162 161 163 162 157 157 157

162 162 161 161 163 158 158 158

 

压缩编码:


解码:


利用MATLAB将测试用例的数据生成jpeg格式图片


将得到后的图片放大:


再将经过JPEG压缩解压后的数据生成jpeg格式图片

 

将得到后的图片放大:

                          

 

四、实验结论、实验体会

    本次实验算是我目前“算法”编码生涯中编码最长的一次,一共700多行的代码。在编码途中我遇到了非常多的问题。

1. 系统问题:在我初次编完750行左右代码的时候,代码突然抽疯,丢失了很多代码,只剩下600行左右,而且有些后面的代码跑到中间去了。点返回键显示返回栈错误,此时我的内心是崩溃的,但是没办法只能重新编写丢失的代码,并对部分代码进行优化修改。然后每写完一段代码,马上新建一个TXT文件保存代码,以防再次发生这种情况。

2. 编程语言问题:在这次编码过程,我愈发的感觉C++/C 类库真的太少了,不利于快速编程。例如:

2.1 string的字符串操作能力及其低下,很多都要自己编写,甚至进行字符串连接时也是非常苛刻,不能将两个常量字符串进行连接、其它类型的数据不能直接跟字符串连接,可用操作函数极少等等,与JAVA语言完全没得比。其次,C++语言的矩阵操作能力也是比较低下的,与MATLAB语言完全没得比,而且我觉得此次的实验更应该用MATLAB语言实现,这样会节省大量的工作;

2.2 用函数返回结构体数组,里面的字符串会出现一些无法处理的乱码,最后不得不将其定义为全局变量;

3. 参照表格繁多复杂、C++/C语言数据类型贫乏:有一些可以通过观察找到规律编写,而有一些则是另外算法得到的结果,因此为方便起见,将一些找不到规律的表直接用映射方法进行存储,这里C++的映射真的太不好了,没有像JAVA那样的哈希数组,操作也麻烦,需要自己定义一个数据类型;

4. 课本出错问题:课本上的IDCT逆变换公式有问题,通过在网上查找正确的公式进行编码;其次课本上给出的测试用例也有一些问题;

5. 编码问题:Z字形编码,编码时通过模拟其轨迹,以及查找规律;

6. 编码问题:代码命名重复,导致一些结果不正确或编译出问题,要时刻明白每个变量的生命周期,尽最大努力缩短变量的生命周期,减少不必要的冲突;

7. 编码问题:对变量的数据类型要时刻有个清晰的认识;

8. 编码规范问题:尽量多的注释,以及对不同类别注释的区分;

9. 不同平台不兼容问题:本次实验我在Dev-C ++开发,而当我把代码放到VS2010时却出现了许多编译错误,需要进行适当修改,VS对语法检查非常苛刻。

    最后,在此次编码过程中我收获颇多,编写了很多非常巧妙的算法,精简了很多常用算法,使得代码效率更高、更简洁、更方便。比如:十进制转换为其它进制的算法,只需要几条非常简短的代码就能实现,根本不用自己编写繁琐的代码,函数原型为char*itoa(int value,char*string,int radix); int value 被转换的整数,char *string 转换后储存的字符数组,int radix 转换进制数,如2,8,10,16 进制等;功能:将任意类型的数字转换为字符串,使用时必须包含<cstdlib>头文件,开启进制转换新玩法。而至于二进制转换为十进制以及二进制串逐位取反的算法也进行了巧妙的设计。

    本来想直接将一张JPEG格式的图片进行压缩编码,然后解压输出,但是经过尝试发现需要编写更庞大的代码,对代码要进行一些修改、增加更多的数据,在时间上是不太允许的,故而没有实现这个想法。


写的不是很好,望各位大神多多指正,不喜勿喷。

原创粉丝点击