图片压缩的正确打开方式

图像通常占据了页面大小的绝大部分,并且占据的绝大部分视觉空间。因此,优化图片通常会节省大量字节数和提升性能:浏览器下载的字节数越少,客户端带宽的争抢越少,浏览器的下载和屏幕加载内容速度越快。

图像优化既是一门艺术,也是一门科学:说它是一门艺术是因为对于如何最好地压缩单个图像并没有一个明确的答案;而说它是一门科学,则是因为有许多成熟的技术和算法可以显著地缩小图像的大小。给图像设置最佳配置需要仔细分析多个维度:格式所具备的能力、编码的内容、质量、像素维度等等。

优化矢量图

所有现代浏览器都支持 SVG,它是一种基于 xml 的二维图片格式。你可以直接在页面上嵌入 svg 标签,也可以作为外部资源引入。绝大多数基于矢量的绘图软件都可以创建 SVG 文件,甚至你也可以直接在编辑器中编辑它们。

<?xml version="1.0" encoding="utf-8"?>
<!-- Generator: Adobe Illustrator 17.1.0, SVG Export Plug-In . SVG Version: 6.00 Build 0)  -->
<svg version="1.2" baseProfile="tiny" id="Layer_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink"x="0px" y="0px" viewBox="0 0 612 792" xml:space="preserve">
<g id="XMLID_1_"><g><circle fill="red" stroke="black" stroke-width="2" stroke-miterlimit="10" cx="50" cy="50" r="40"/></g>
</g>
</svg>

上面的例子渲染了下面这个简单的圆形,有黑色的轮廓和红色的背景。

可以看出,它包含很多元数据,比如层信息、注释,以及在浏览器中不需要的 xml 命名空间。你可以使用 SVGO这类工具来压缩 svg 文件大小。

SVGO 将上述的 SVG 文件的大小减少了58%,从 470 字节减少到 199 字节。

<svg version="1.2" baseProfile="tiny" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 612 792"><circle fill="red" stroke="#000" stroke-width="2" stroke-miterlimit="10" cx="50" cy="50" r="40"/></svg>

因为 SVG 是一种基于 xml 的格式,所以还可以应用GZIP 压缩来减少传输大小。但是你需要先在服务器配置好压缩相关的配置。

一个栅格图像只是单个“像素”的二维网格,例如,一个100x100 像素的图像是一个 10,000 像素的序列。每个像素都存储了“RGBA”值:®红色波段,(G)绿色波段,(B)蓝色波段,(A) alpha 透明波段。

在浏览器内部,为每个波段配置了 256 个值,每个波段占用了 8 bit(2 ^ 8 = 256),所以每像素占用了 4 字节(4波段 x 8 bit = 32 bit = 4字节)。因此,如果我们知道栅格图片的尺寸,就可以轻松地计算文件大小

  • 100x100像素的图像由10,000像素组成
  • 10,000像素 x 4字节= 40,000字节
  • 40,000字节/ 1024 = 39 KB

(看不懂计算的可以看文末,有详细例子)

顺便提一下,不管传输的图像格式是什么,当图像被浏览器解码时,每个像素总是占用4个字节的内存。对于大型图像和没有大量可用内存的设备(例如低端移动设备)来说,这可能引发性能问题。

尺寸 像素 文件大小
100 x 100 10,000 39 KB
200 x 200 40,000 156 KB
300 x 300 90,000 351 KB
500 x 500 250,000 977 KB
800 x 800 640,000 2500 KB

对于一张 100x100 像素的图片来说,39kb 好像没什么问题。但是当尺寸变大时,文件大小会急速膨胀,使得下载耗费的性能变得很昂贵。

这篇文章到目前为止只关注“未压缩”的图像格式。值得庆幸的是,我们通过一些操作来优化图像文件的大小。

一个简单的策略是将图像的“位深度”降低:降低到每波段 8bit。每个波段占 8 bit 给了每个波段 256 个值和 16,777,216 (256 ^ 3) 种颜色。如果我们把颜色调整到 256 种会发生什么呢?原本占用 8 bit 的 rgb现在只占用了 7 bit ,那么每像素就节省了 2 字节(参考上面的公式)。这比原先的每像素 4 个字节压缩了 50%!

具有渐变颜色的复杂场景(例如,渐变或天空)需要更多的颜色来避免失真,比如上面第三张图片的像素化天空。从另一个角度来看,如果图片只使用了很少的颜色,那么颜色数量过多只会浪费宝贵的文件体积而已。

接下来你会发现,一旦你优化了其中一个像素的数据,那么你还可以巧妙地查询到附近的像素:事实上,许多图像,尤其是照片,都有许多相近颜色的像素——例如:天空,重复的纹理等待。利用这些信息,压缩器可以应用增量编码。不是存储每个像素的值,而是存储和附近像素的差异:如果相邻像素相同,则设置为”零“,只需要花费 1 bit!

当然,我们不能在这里就停下脚步。

人眼对不同的颜色有不同程度的敏感度:你可以通过减少或增加颜色位深度来优化你的颜色编码,从而实现这一点。“附近”的像素会形成一个二维网格。这意味着每个像素都有多个邻居:你可以利用这个特性来进一步改进增量编码。我们可以不用查看每个像素的相邻像素,而是查看一个较大的元素块,并使用不同的设置对不同的元素块进行编码。

我们可以发现,图像的优化逐渐变得复杂了起来(或者说有趣了起来,这取决于你自己的观点),并且这是学术和商业研究的比较活跃的领域。图像占用了大量的字节,因此开发更好的图像压缩技术具有很大的价值。如果您想了解更多信息,请访问Wikipedia page,或者查看WebP 压缩技术白皮书以获得实际示例。

那说了那么多牛逼的,学术性的内容,它如何才能帮助我们优化网站上的图片呢?理解问题的关键是很重要的:RGBA像素、位深度和各种优化技术。在开始讨论各种栅格图像格式之前,理解并记住所有这些概念都是非常重要的。

无损图像压缩与有损图像压缩

对于某些数据类型的压缩,例如页面的源代码和可执行文件,最关键的是:压缩程序不能更改或丢失任何原始信息。一个确实或错误的数据可能会完全改变文件的内容和含义。而对于其他一些类型的数据,如图像、音频和视频,压缩后交付原始数据“近似”的表达,是完全可以接受的。

事实上,由于眼睛的工作原理,我们常常可以丢弃每个像素的一些信息,以减少图像的文件量——例如:我们的眼睛对不同的颜色有不同的敏感度,这意味着我们可以用更少的 bit 来编码一些颜色。因此,一个典型的图像优化流程是由两个高级步骤组成的:

  1. 图像通过有损过滤器处理,消除一些像素数据。
  2. 图像通过无损过滤器处理,压缩像素数据。

第一步是可选的,是否使用将取决于特定的图像格式,但最重要的是在于理解:任何图像都可以经过有损压缩来减小体积。事实上,各种图像格式(如GIF、PNG、JPEG和其他格式)之间的区别在于它们在应用有损压缩和无损压缩时所使用(或省略)的特定算法的组合。

那么,有损和无损优化的“最优”配置是什么呢?这答案取决于图像内容和你自己的标准,比如通过有损压缩优化文件大小和失真之间的权衡:在某些情况下,您可能希望跳过有损压缩,以完全保真的方式传递复杂的细节。这就是它没有统一的标准的原因,这也是发挥你自己判断能力的地方。

作为一个动手操作的例子,当使用有损格式(例如JPEG)时,压缩程序通常会公开一个可定制的“质量”设置(例如,Adobe Photoshop中的“保存为Web”功能提供的质量选项),那通常是1到100之间的数字,它控制着特定的有损和无损算法集合。为了获得最佳效果,可以尝试各种图像质量,不要害怕降低降低画质——一般情况下视觉效果不会减弱太多,但是文件大小可能会减小很多。

注意,由于编码图像的算法不同,不同图像格式的质量等级不能直接进行比较:值为 90 的高质量 JPEG 与相同值的 WebP 格式将产生完全不同的结果。事实上,即使是相同图像格式,不同质量级别也可能根据压缩器的实现算法而产生明显不同的输出。

图像优化清单

当你在优化你的图像时,要记住一些技巧和技巧

  • 优先使用矢量格式:矢量图像的分辨率和大小是独立的,这让它非常适合多设备和高分辨率的情况。
  • 缩小和压缩 SVG 资源:
    • 大多数绘图应用程序生成的 XML 标记通常包含可删除的和不必要元数据;
    • 确保您的服务器为 SVG 资源设置了 GZIP 压缩
  • 优先使用 WebP 而不是栅格图片:WebP 格式的图片大小通常会比旧格式小很多
  • 选择最佳栅格图像格式:确定你的功能需求,并选择适合它们需求的格式。
  • 多对栅格图片的最佳质量进行试验:不要害怕降低质量,通常显示结果是很不错的,而且大小节省非常明显
  • 删除不必要的图像元数据:许多栅格图像包含有关资源的不必要的元数据,例如地理信息、相机信息,等等。使用适当的工具去除这些数据。
  • 提供缩放后的图片:调整图像大小,并确保“显示”尺寸尽可能接近图像的“自然”尺寸。尤其要密切关注大型图像,因为它们占用了最大的开销。
  • 自动化,自动化,自动化!投资自动化工具和前端基建,以确保你的所有图片资源始终都被优化。

译者的话

这篇文章干货满满,建议看两遍。虽然都是学术性的知识点,但是知识的广度是非常重要的,说不定哪天就用到了呢?

开篇讲解了 SVG 的原理,SVG 图片一般是用作 icon,其实我们能够操作的并不多,只要注意开启 GZIP 即可。

再讲到了栅格图片的原理,栅格图片是我们最常用的图片格式。栅格图片的本质就是在每个像素点的位置存放一段表示颜色的 RGB 值。因为 255 = 2^8,二进制表示也就是 11111111,占用了 8 个比特;再由于 RGBA 有四个波段(红、黄、蓝、透明),一个 rgba 的白色用二进制表示就是(11111111,11111111,11111111,11111111),占用了 24bit,1 字节 = 8bit,所以一个 rgba 颜色就占用了 4 字节。再看一张 100x100 的图片,有 10,000 个像素,每个像素 4 字节所以就占用了 40000 字节。这就是一张栅格图片的计算方法了。

栅格图片的压缩一直是学术界的重中之重,压缩分为两种,有损和无损。

有损的原理是将人眼难以辨别的相似的颜色归为一类,直接以颜色相同处理(用 0 标识),这样有损图片画质。

无损的原理是只将附近相同的颜色标识为 0,保证数据不丢失和可还原。

一般我们会将两者结合使用,权衡画质和体积大小的优缺点,选取最优解。

最后总结了优化图片的一些经验,总而言之收获满满,是一篇高质量科普文。

欢迎关注我的个人微信公众号:前端 stack,每周分享一篇外文技术翻译哦


原文传送门

图片压缩的正确打开方式相关推荐

  1. TinyPng图片压缩的正确打开方式

    https://tinypng.com/ TinyPNG使用智能的「有损压缩技术」来减少WEBP.JPEG和PNG文件的文件大小.通过选择性地减少图像中的「颜色数量」,使用更少的字节来存储数据.这种效 ...

  2. 揭秘超分辨率的正确打开方式

    写在前边:图像和视频通常包含着大量的视觉信息,且视觉信息本身具有直观高效的描述能力,所以随着信息技术的高速发展,图像和视频的应用逐渐遍布人类社会的各个领域.近些年来,在计算机图像处理,计算机视觉和机器 ...

  3. python论文参考文献名称_Word的正确打开方式(附毕业论文模板)

       ----点击蓝字关注我呀---- 三年前的我搞毕业设计,第一次接触这玩意儿,一脸懵逼 好在我朱哥搞过大创(还是国家级的),当时给我各种科普单片机的知识 搞大创的好处就是当我们不知道是画机械图还是 ...

  4. wps的流程图怎么导出_word流程图-WPS绘制流程图的正确打开方式,超级简单

    不知道大家在办公的时候习惯使用什么版本的软件?这几天小编在绘制流程图的时候发现一个特别有意思的,你会绘制带有动态走向的流程图吗?不信你看 看起来是不是挺高大上的,你知道是怎么完成的吗?今天小编大家快速 ...

  5. 肖秀荣、陆寓丰、徐涛三大名师的正确“打开方式”

    考研政治怎么学? 肖秀荣.陆寓丰.徐涛 三大名师的正确"打开方式" HEY 暑假黄金期到达尾声,是不是有很多小伙伴还没有开始政治复习?或者复习的迷迷糊糊? 今天笔者会为大家进行全面 ...

  6. Python Matplotlib绘图的正确打开方式

    Python Matplotlib绘图的正确打开方式 文章目录 Python Matplotlib绘图的正确打开方式 1.先搞懂fig.axes.axis `Figure` `Axes` `Axis` ...

  7. 这才是目前百度统计接口的正确打开方式20180322

    这才是目前百度统计接口的正确打开方式20180322 关于百度统计接口的说明 1.登陆接口网站找到的有2种方式 第一种调用(不能用) https://api.baidu.com/sem/common/ ...

  8. win10系统rar文件的正确打开方式

    rar文件怎么打开?基本上所有的windows电脑用户都会有接触到rar文件,特别是我们在传输大文件夹的时候rar文件可以说是必备的.但是最近很多升级到win10系统的用户发现自己的rar文件夹打不开 ...

  9. 二次元的正确打开方式

    本文 GitHub https://github.com/Jack-Cherish/PythonPark 已收录,有技术干货文章,整理的学习资料,一线大厂面试经验分享等,欢迎 Star 和 完善. 一 ...

最新文章

  1. ACM寒假训练第一周总结
  2. 杭电 HOJ 1251 统计难题 解题报告
  3. AB1601 IO口反应延时的问题
  4. 【算法学习笔记】哈夫曼树的构建和哈夫曼编码的实现代码
  5. Python能做什么事?为什么人工智能一定要学Python?
  6. HttpServletResponse和HttpServletRequest详解——Web网络学习笔记
  7. mysql重置root密码方法
  8. [C/C++] 结构体存储问题
  9. 【Chia开发文档】Offer 类的属性、使用方法、作用及返回值
  10. 垃圾分类小程序 — 微信小程序源码分享
  11. 第一篇博客:A+B Problem
  12. springboot+shrio简易登录登出和用户权限认证。
  13. Android5.0新特性:RecyclerView实现上拉加载更多
  14. [MakeFile教程-09] 隐含规则
  15. 谈谈制造企业如何制定敏捷的数字化转型策略
  16. Python-turtle模块绘图(升国旗)
  17. 【基础知识】~ 竞争/冒险
  18. JS获取节点的兄弟,父级,子级元素
  19. 数字电路实验六:同步模4可逆计数器设计预实验报告
  20. 查询农历阳历过生日人员

热门文章

  1. 《D o C P》学习笔记(5 - 1)Dealing with Uncertainty Through Probability - Lesson 5
  2. 赛门铁克召开2010财年中国合作伙伴高峰会
  3. Python爬虫实战 - 电影榜单Top250
  4. 微信小程序 —— 自定义长圆形view
  5. 使用sendmail发送email
  6. Tensorflow2.1入门 第六章:循环神经网络
  7. 数学实验3:插值与拟合
  8. 基于微信小程序视频点播系统 视频点播小程序毕业设计 毕业论文 开题报告和效果图参考
  9. AES加密:PHP与Java互通问题
  10. 安卓手机开不了机_手机开不了机的原因 _手机开不了机如何解决