1

在过去的几天里,我对 PNG 做了一些摆弄,我对我的发现感到不安。我的结论是,我的大部分结果都与压缩有关。所以这个周末我将深入研究高级压缩文章。到目前为止,我想分享我的发现。看看是否有人对实现我的目标有任何建议,并可能为我指明正确的方向。

我目前正在做一个项目,我需要在不到 15 秒的窗口内获得尽可能小的文件大小。

我正在使用的大多数图像都是具有完整 256 调色板的 PNG-8bpp。我可以用 5bpp(32 色)准确地表示这些图像中的大多数。

但是,PNG 索引仅支持 1、2、4 和 8bpp。所以我的想法是将 PNG 格式剥离为我需要的最少信息,并编写一个编码器/解码器来支持 3、5、6 或 7bpp 的 IDAT 部分。

Test 1:
Original File: 61.5KB, 750 * 500, 8pp Palette, 256 colors, No tRNS
After Optimizations (Reductions to 4bpp, Strip Anx Chunks, & PNGOUT): 49.2KB 4bpp, 16 Colors
Human Interpretation: I can see 6 distinguishable colors.

由于我只需要六种颜色来表示图像,因此我决定使用 3bpp 对 IDAT 进行编码,以提供最多 8 种颜色的调色板。首先,我解压缩了 IDAT,得到了 368KB 的新文件大小。在对 IDAT 应用 3bpp 后,我新的未压缩文件大小为 274KB。我的开始似乎是一个好的开始……接下来我将 deflate 应用到我的新 IDAT 部分。结果... 59KB。

比使用 4bpp 大 10KB。

Test 2:
Original File: 102KB, 1000 * 750, 8bpp, 256 Colors, tRNS 1 fully transparent color
After Optimization: 79KB, 8bpp, 193 colors, tRNS 1 full transparent color
Human Interpretation: I need about 24 colors to represent this picture.

24 种颜色可以在 5bpp 中以 32 种颜色表示。使用上述相同的技术,我能够获得比未压缩更好的结果,但我再次在压缩时失败了。最终大小压缩... 84KB。然后我尝试了 6,7bpp... 与 8bpp 相同的结果压缩更差。

只是为了确保我保存了所有未压缩的图像并尝试了其他几种压缩算法...... LZMA、BZIP2、PAQ8......同样的结果是 8bpp 的压缩大小比 5,6 或 7bpp 更小,4bpp 的压缩大小比 3bpp 更小.

为什么会出现这种情况?我可以调整/修改压缩算法以针对使用 5,6 或 7bpp 格式的类似 PNG 的格式来进行 8bpp 压缩吗?值得花时间吗……是的,再节省 10KB 是值得的。

4

2 回答 2

2

您所看到的是,通过使用奇数像素大小,由于 PNG 压缩的工作方式,您的有效压缩率会降低。与直接使用 FLATE/ZIP 压缩相比,PNG 压缩的优势在于过滤。PNG 压缩试图利用少量预处理过滤器来利用水平和垂直对称性。这些过滤器在字节边界上工作,并且对 4/8/16/24/32/48/64 位的像素大小有效。当您移动到一个奇数大小的像素(3/5/6/7 位)时,您正在击败过滤,因为在 8 位边界上过滤时,相同颜色的像素不会水平“相互抵消”。

即使过滤不是问题,FLATE 压缩的工作方式,将像素大小从 8 位减少到 7 位或 6 位也不会产生太大影响,因为它还假设符号大小为 8 位。

总之......通过使用奇数大小的像素可以获得的唯一好处是未压缩的数据会更小。通过破坏像素的字节边界对称性,您会破坏 PNG 压缩的大部分好处。

GIF 压缩支持从 1 到 8 位的所有像素大小。它将符号大小定义为像素大小,并且不使用任何预过滤。如果将 8 位 GIF 图像压缩为 7 位像素,则不会受到更少的压缩,但也不会受益,因为压缩更多地取决于像素的重复而不是符号大小。

于 2012-02-26T04:17:28.970 回答
0

PNG 使用的 DEFLATE 压缩有两种主要技术:

  • 找到重复的字节序列并将它们编码为反向引用
  • 使用霍夫曼编码对字节进行编码

通过从 8 位更改像素长度,您将与字节边界不同步,并且 DEFLATE 将无法将重复的像素运行编码为重复字节。

并且由于霍夫曼编码,8位像素有未使用的位并不重要,因为编码将使用可变宽度代码对字节进行编码,将最短的代码分配给最频繁出现的值。

于 2013-03-07T14:36:45.003 回答