JPG、PNG和GIF图片的基本原理及优化方法




一提到图片,我们就不得不从位图开始说起,位图图像(bitmap),也称为点阵图像或绘制图像,是由称作像素(图片元素)的单个点组成的。这些点可以进行不同的排列和染色以构成一副图片。当放大位图时,可以看见赖以构成整个图像的无数单个方块。

我们常见的图片格式中JPG、PNG、GIF亦属于位图,所以它们的数据结构大致相同,只是每一种图片格式都有不同的压缩算法,不同的扫描方式,但是优化的方法都有一个共同点,都是围绕着每个像素颜色值来下手,那么我们具体该如何进行优化呢?下面我就借助马海祥博客的平台来给大家介绍一下图片的一些基本原理和优化的方法:

一、JPG图片的原理与优化

JPG是一种对彩色或灰阶之类连续色调图形作压缩和解压缩的标准,这个标准是由ISO/IEC JTC1/SC29 WG10所订定。

压缩算法为正、反离散余弦转换,如下图所示:

如果是反离散余弦转换即把整个流程反转。

马海祥提醒大家一点:这里的8X8像素区块是我们JPG优化方法的重点,在之后会涉及到取样、区块量化、扫描的步骤,然而取样、区块量化这两个步骤将是导致图像失真的过程,也是我们优化工作所涉及到核心部分。

1、取样

这里所提到的可以很好的解释到下面JPG优化方法中的色彩优化;

JPG将不同的色彩当作独立的成份,因此各个成份可以被视为一个灰阶影像来处理,如果各个颜色成份间没有关联性时.便可以将压缩的效果处理得最好,因此把红(R)、绿(G)、蓝(B)的成份转换成:亮度
(Luminance)(Y)、色度 (Chrominance)(Cb和 Cr),使得各项没有关联的成份:

Y = 0.299R+0.587G+0.144B

  Cb = -0.169R-0.331G+0.500B

  Cr = 0.500R- 0.419G –0.081B

由于人的视力系统对色度的敏锐度不高
,因此以YCbCr色度的方式来表示可以再做一次作取样(Subsampling)来减低信息量,如下图所示:

4:4:4格式代表YCbCr原来完整的信息,可以再次取样以4:2:2或4:2:0格式来表达;4:2:2格式将原本的信息量减少为三分之二,而4:2:0格式则可以将信息三减少为一半。虽然色度的信息量减少了.但对人的视觉神经而言却仅仅感受到微小的差别而已。

2、区块量化

为了说明执行离散余弦转换(DCT)的影响,我们将一张图去下的8×8区块的亮度资料转换成符合DCT运算范围内的系数表,如下图所示:

低频部分包含了区块的大部分能量,而对视觉较不敏感的高频部分,则通常只含有较低的能量。

接下来对亮度系数做量化处理的矩阵系数表,如下图所示:

在亮度系数的量化方面每个DCT系数除以相对的量化矩阵的值,在四舍五入后得到如下的量化后DCT系数(例如-80/16=-5),如下图所示:

注意量化后区块高频部份出现许多零值,代表人类视觉系统对高频部份并不敏感。由于四舍五入的部份并不能在解码时重现,因此这个步骤将是个失真的过程。

3、扫描

区块在量化之后,只有低频的部分有非零值,为了进一步地减少储存空间的大小,尽可能地将零值放在一起,使得处理时能以几个零来表示而非个别的处理每个零,因此运用了如下图的方式做斜向扫描:

这种斜向扫描的扫描线乃是沿着空间频率大小增加的方向作扫描的,使得许多的零可以被串接在一起,以达到更好的效果。

了解上述3个流程后,后续我们做JPG优化的时候会更得心应手了,如何处理颜色,如何减少颜色数值而却又最少的减少图片失真的比率。

接下来马海祥就为大家介绍下JPG常用的几种优化方法:

1、8像素栅格

如下面这2副图片所示,图片为32X32,白色方块宽高为8X8:

正如大家看到的,左上角的小方块正好对齐在“8像素栅格”,这样就确保小方块保持是锐利。当保存的时候,图片会被分成许多的8×8
px的区块,而软件是对每一个区块进行独立优化的。由于右下方的方块并不匹配这些区块(也就是这个方块跨越了几个区块,正好落于区块的交接线上),优化器在寻找索引的时候就会在黑色和白色之间寻找平衡,即添加了杂色。

8像素栅格示例:

不仔细看可能发现不了,第二幅图片中盒子的黑子盖子左边超出的区域、99数字超出的多余像素均已删除,198.00元下移了一个像素,3个很简单的操作便可减少约1K,做到这一步,大家肯定会考虑一个问题,难道每次做图的时候都要拉着么辅助线不麻烦么?

其实,这里只是为了做一个精确的示范,如果应用到工作中,我们大可将8X8的辅助方格改为16X16或者32X32。

2、图片质量

不要保存质量为100的图片。这个并不是最高质量的图片,只是一个数值上的优化底线,最终你会得到一个不合理的大文件。事实上把质量设置在95以上就已经足以防止丢失信息了。

在质量上有个分水岭,这就是我们通常建议JPG质量最好是在60左右的原因。当在Photoshop中把质量设置低于51的时候,它就会执行另一个叫做“降色采样(原文:color
down-sampling)”的优化算法,它会在8个像素周围平均采样,这样会在边缘产生杂色。

因此,如果图片很小而且对比很大,建议在Photoshop中不要设置质量低于51。

图例(左为质量51右为质量50):

3、色彩优化

这里优化的原理在于解压缩过程,反量化与斜向扫描中着手。这里涉及到两个量化矩阵(亮度与色度)的处理。

但是此方法用到的情况相对比较少,所以这里只做简短的介绍。

Photoshop有一个Lab的颜色模式,L表示亮度(Luminosity),a表示从洋红色至绿色的范围,b表示从黄色至蓝色的范围。

其中在这里最重要的就是明度(也称为亮度),优化图像的时候通常是压缩颜色通道,但尽可能保持高亮的亮度通道,因为人们对它最为敏感。

马海祥提醒大家一点,这里最关键的是滤镜>>杂色>>中间值针对A,B两个通道的颜色做处理。

二、PNG图片的原理与优化

PNG,图像文件储存格式,其目的是试图替代GIF和TIFF的文件格式,同时增加一些GIF所不具备的特性。PNG提供5种图片类型:灰度,真彩色,索引色,带alpha通道的灰度,带alpha通道的真彩色,遗憾的是Photoshop只能导出3种图像类型:带透明的索引颜色,真彩色,带透明度的真彩色。

对于PNG图像,可以分为索引(Index)图和RGB图两种,索引图只包含固定数量的颜色,而RGB图的颜色数量是不受限制的。

索引图:为节约存储,把图像中使用的颜色与一个颜色表对应起来,索引色常使用16色、32色、64色、128色或256色等,但最多不得超过256色;

RGB图:的每一个象素都保存一个RGB值,代表这个象素的颜色,因此,一张RGB图有多少个象素,文件中就保存多少个RGB值。

1、压缩

PNG采取的是LZ77无损数据压缩算法:LZ77算法简单来说就是通过使用编码器或者解码器中已经出现过的相应匹配数据信息替换当前数据从而实现压缩功能。

最重要的还是线性过滤(也称为“三角过滤”),PNG有5种过滤器,None(无过滤),Sub(当前值减去左侧像素的值),Up(减去上方像素的值),Average(减去左侧和上方像素的平均值)和Paeth(替换上方,左边或者上方的左边像素值,并重新以Alan
Paeth命名)。下面只举例其中之一的Up过滤:

以数字2为标识的每一行都经过了“Up过滤”,“Up过滤”向 png
解码器发送信息:“对于当前的像素,提取上方像素的值,并将其添加到当前值”。图中第2-5行垂直方向都拥有相同的值。所以它们的值都是0,如果这样的图片越大那么压缩比率也越大。

2、扫描

PNG的扫描方式很简单,只存在两种:非隔行扫描、Adam7(7遍隔行扫描方法)

Adam7(由Adam M. Costello开发的7遍隔行扫描方法),原理如下图所示:

图片示例:

马海祥博客常用的两种PNG优化方法:

1、色调分离

优化原理:有效的减少色彩数,合并相似的颜色,创建出色调区域,更好的执行“线性过滤”,得到高压缩率。

缺点:这种方法有一定的局限性,尤其是优化的图片与 html 背景融合的情况下须慎用。

这里的色阶值可根据实际情况设置:

2、图层分离

有时候因为图片中存在一些半透明像素,不得不保存一个“重量级”的PNG-24文件。如果将此类图像一分为二,一部分是不透明像素,另一部分则为半透明,然后各以适当格式保存。

比如你可以用PNG-24格式保存半透明像素,而不透明像素则用PNG-8甚至JPEG格式保存。

例如:

马海祥博客推荐的操作步骤:

(1)、在图层面板中Ctrl+左键单击图层建立选区;

(2)、切换至通道面板,将选区储存为通道;

(3)、选择该通道,取消选区,将阈值(图像 -> 调整 -> 阈值)调至255;

(4)、再次Ctrl+左键单击该通道建立选区并隐藏该通道,然后选择原始图层,打开图层 -> 新建 ->
通过剪切的图层,即能得到上面两幅分离后的图片。

(5)、可再次对两幅图片进行色调分离等方法进行优化。

此方法类似活动中背景图过大时进行分割是为同一个道理,多增加一个请求而把图片拆分,进行叠加。

三、GIF图片的原理与优化

由于GIF现在使用率偏低,除非需要用到GIF动画,由于PNG本身是开发者为了代替GIF而衍生出的图片格式,所以透明图片建议采用PNG8。下面马海祥就简单的介绍下GIF的原理:

GIF(Graphics Interchange
Format)的原义是“图像互换格式”,是CompuServe公司在1987年开发的图像文件格式。GIF文件的数据,是一种基于LZW算法的连续色调的无损压缩格式。其压缩率一般在50%左右,它不属于任何应用程序。GIF格式的另一个特点是其在一个GIF文件中可以存多幅彩色图像,如果把存于一个文件中的多幅图像数据逐幅读出并显示到屏幕上,就可构成一种最简单的动画。

GIF格式的特点是压缩比高,磁盘空间占用较少,所以这种图像格式迅速得到了广泛的应用。最初的GIF只是简单地用来存储单幅静止图像(称为GIF87a),后来随着技术发展,可以同时存储若干幅静止图像进而形成连续的动画,使之成为当时支持2D动画为数不多的格式之一(称为GIF89a),而在GIF89a图像中可指定透明区域,使图像具有非同一般的显示效果,这更使GIF风光十足。在Internet上大量采用的彩色动画文件多为这种格式的文件,也称为GIF89a格式文件。

此外,考虑到网络传输中的实际情况,GIF图像格式还增加了渐显方式,也就是说,在图像传输过程中,用户可以先看到图像的大致轮廓,然后随着传输过程的继续而逐步看清图像中的细节部分,从而适应了用户“从朦胧到清楚”的观赏心理。

但GIF有个小小的缺点,即不能存储超过256色的图像。尽管如此,这种格式仍在网络上大行其道应用,这和GIF图像文件短小、下载速度快、可用许多具有同样大小的图像文件组成动画等优势是分不开的

LZW压缩算法

LZW就是通过建立一个字符串表,用较短的代码来表示较长的字符串来实现压缩,字符串和编码的对应关系是在压缩过程中动态生成的,并且隐含在压缩数据中,解压的时候根据表来进行恢复,算是一种无损压缩。

例如:

正常文本:好人经常说自己是好人,但是我确实是个好人。

压缩文本:$1经常说自己是$1,但是我确实是个$1. $1=[好人]

马海祥博客知识扩展:

除基本的灰度“红绿蓝”(外语简称:rgb)或“青色、洋红、黄、黑”(外语简称:cmyk)和“轻盈a-b”(外语简称:lab)模式之外,photoshop支持(或处理)其他的颜色模式,这些模式包括位图模式、灰度模式、双色调模式、索引颜色模式和多通道模式。并且这些颜色模式有其特殊的用途。例如,灰度模式的图像只有灰度值而没有颜色信息;索引颜色模式尽管可以使用颜色,但相对于rgb模式和cmyk模式来说,可以使用的颜色真是少之又少。下面就来介绍这几种颜色模式。

1、位图(bitmap)模式

位图模式用两种颜色(黑和白)来表示图像中的像素。位图模式的图像也叫作黑白图像。因为其深度为1,也称为一位图像。由于位图模式只用黑白色来表示图像的像素,在将图像转换为位图模式时会丢失大量细节,因此photoshop提供了几种算法来模拟图像中丢失的细节。

在宽度、高度和分辨率相同的情况下,位图模式的图像尺寸最小,约为灰度模式的1/7和rgb模式的1/22以下。

2、灰度(grayscale)模式

灰度模式可以使用多达256级灰度来表现图像,使图像的过渡更平滑细腻。灰度图像的每个像素有一个0(黑色)到255(白色)之间的亮度值。灰度值也可以用黑色油墨覆盖的百分比来表示(0%等于白色,100%等于黑色)。使用黑折或灰度扫描仪产生的图像常以灰度显示。

3、双色调(duotone)模式

双色调模式采用2-4种彩色油墨来创建由双色调(2种颜色)、三色调(3种颜色)和四色调(4种颜色)混合其色阶来组成图像。在将灰度图像转换为双色调模式的过程中,可以对色调进行编辑,产生特殊的效果。而使用双色调模式最主要的用途是使用尽量少的颜色表现尽量多的颜色层次,这对于减少印刷成本是很重要的,因为在印刷时,每增加一种色调都需要更大的成本。

4、索引颜色(indexed
color)模式

索引颜色模式是网上和动画中常用的图像模式,当彩色图像转换为索引颜色的图像后包含近256种颜色。索引颜色图像包含一个颜色表。如果原图像中颜色不能用256色表现,则photoshop会从可使用的颜色中选出最相近颜色来模拟这些颜色,这样可以减小图像文件的尺寸。用来存放图像中的颜色并为这些颜色建立颜色索引,颜色表可在转换的过程中定义或在声称索引图像后修改。

5、多通道(multichannel)模式

多通道模式对有特殊打印要求的图像非常有用。例如,如果图像中只使用了一两种或两三种颜色时,使用多通道模式可以减少印刷成本并保证图像颜色的正确输出。

6、8位/16位通道模式

在灰度“红绿蓝”(外语简称:rgb)或“青色、洋红、黄、黑”(外语简称:cmyk)模式下,可以使用16位通道来代替默认的8位通道。根据默认情况,8位通道中包含256个色阶,如果增到16位,每个通道的色阶数量为65536个,这样能得到更多的色彩细节。photoshop可以识别和输入16位通道的图像,但对于这种图像限制很多,所有的滤镜都不能使用,另外16位通道模式的图像不能被印刷。

本文为马海祥博客原创文章,如想转载,请注明原文网址摘自于http://www.mahaixiang.cn/Photoshop/400.html,注明出处;否则,禁止转载;谢谢配合!

最新文章

  1. hdu 2516 FIB博弈
  2. 【Android】 Android实现录音、播音、录制视频功能
  3. js中的预加载与懒加载(延迟加载)
  4. Java IO读取文件之二
  5. js方法和prototype
  6. 百度地图API示例之小实践 添加代理商标注
  7. Nginx负载均衡介绍
  8. CenOS搭建FTP服务器
  9. switch case实现两个数的算术运算
  10. Eclipse插件Mylyn管理上下文任务管理
  11. java的wait和notifyAll使用方法
  12. java集合系列
  13. scope引起的问题
  14. SQL Server Compact/SQLite Toolbox 使用
  15. G彩娱乐网一个程序员到一个销售高手的心路历程
  16. linux下ftp命令的安装与使用
  17. 读Zepto源码之内部方法
  18. Fiddler抓包【4】_重定向AutoResponder
  19. 简单易懂的程序语言入门小册子(5):基于文本替换的解释器,递归,不动点,fix表达式,letrec表达式
  20. 【POJ2182】Lost Cows 树状数组+二分

热门文章

  1. JS 无法清除Cookie的解决方法
  2. swift3.0 对UITextField()输入框输入的内容进行监控
  3. 字符串--hdu--3783--ZOJ
  4. Java微信公众平台开发之扫码支付模式二
  5. Hibernate(三)
  6. Windows 程序注册成服务的方法
  7. python学习之核心数据类型
  8. get,post,jsonp数据交互—百度下拉列表
  9. noip普及组2005 陶陶摘苹果
  10. Zim学习笔记 (Fedora)