【问题标题】:Java Deflater strategies - DEFAULT_STRATEGY, FILTERED and HUFFMAN_ONLYJava Deflater 策略 - DEFAULT_STRATEGY、FILTERED 和 HUFFMAN_ONLY
【发布时间】:2011-02-01 09:34:12
【问题描述】:

在压缩 Java webapp 响应时,我试图在性能和压缩程度之间找到平衡。

在查看 Deflater 类时,我可以设置一个级别和一个策略。这些级别是不言自明的 - BEST_SPEEDBEST_COMPRESSION

我不确定策略 - DEFAULT_STRATEGYFILTEREDHUFFMAN_ONLY

我可以从 Javadoc 中找到一些意义,但我想知道是否有人在他们的应用程序中使用了特定策略,以及您是否发现在性能/压缩程度方面有任何差异。

【问题讨论】:

    标签: java compression gzip deflate


    【解决方案1】:

    Java Deflater 中提到的策略选项,我相信起源于 ZLIB 和 (RFC 1950) 和 DEFLATE (1951) 的 zlib (C) 实现。它们几乎存在于所有实现 DEFLATE 的压缩库中。

    要了解它们的含义,您需要对DEFLATE 有所了解。压缩算法结合了 LZ77 和 Huffman 编码。基础是:

    • LZ77 压缩通过查找重复的数据序列来工作。实现通常使用 1k 到 32k 之间的“滑动窗口”来跟踪之前的数据。对于原始数据中的任何重复,LZ77 压缩不会在输出中插入重复数据,而是插入“反向引用”。想象一下后面的引用说“在这里,插入你在 8293 字节前看到的相同数据,共 17 个字节”。 back-ref 被编码为这对数字:长度 - 在本例中为 17 - 和距离(或偏移量) - 在本例中为 8293。

    • 霍夫曼编码用代码代替实际数据。当数据显示 X 时,Huffman 代码显示 Y。这显然有助于压缩,仅当替代比原始短时。 (一个反例是在 Jim Carrey 的电影 Yes Man 中,当 Norm 使用“Car”作为 Carl 的简称。Carl 指出 Carl 已经很短了。)霍夫曼编码算法进行频率分析,并使用最常出现的数据序列的最短替代。


    Deflate 结合了这些,因此可以在 LZ77 反向引用上使用 Huffman 代码。各种 DEFLATE/ZLIB 压缩器的策略选项只是告诉库 Huffman 与 LZ77 的权重。

    • FILTERED 通常意味着 LZ77 匹配在长度为 5 处停止。所以当文档说时

      使用(过滤)过滤器(或预测器)生成的数据,...过滤后的数据主要由具有某种随机分布的小值组成。

    (来自the zlib man page
    ...我对代码的阅读表明它进行 LZ77 匹配,但最多只能匹配 5 个或更少字节的序列。我猜这就是文档所说的“小值”的意思。但是文档中没有提到数字 5,因此不能保证数字不会从 rev 更改为 rev,或从 ZLIB/DEFLATE 的一个实现更改为另一个(如 C 版本和 Java 版本)。

    • HUFFMAN_ONLY 说,只做基于频率分析的替换代码。 HUFFMAN_ONLY 非常非常快,但对大多数数据的压缩效果不是很好。除非您的字节值范围非常小(例如,如果实际数据流中的字节仅采用可能的 255 个值中的 20 个),或者以牺牲大小为代价对压缩速度有极高要求,HUFFMAN_ONLY 将不是你想要的。

    • DEFAULT 以作者预期的方式将两者结合起来,它将对大多数应用程序最有效。


    据我所知,在 DEFLATE 中没有办法只做 LZ77。没有LZ77_ONLY 策略。但当然,您可以构建或购买自己的 LZ77 编码器,这将是“仅限 LZ77”。


    请记住,该策略永远不会影响压缩的正确性;它只影响它的运行,以及它的性能,无论是速度还是大小。


    还有其他方法可以调整压缩器。一是设置LZ77滑动窗口的大小。在 C 库中,这是使用“窗口位”选项指定的。如果您了解 LZ77,那么您就知道较小的窗口意味着更少的回溯,这意味着更快的压缩,但会丢失一些匹配项。这通常是压缩时更有效的旋钮。


    底线是,对于 80% 的情况,您不需要调整策略。您可能对摆弄窗口位感兴趣,只是想看看会发生什么。但只有在您完成了您需要在应用中执行的所有其他操作后才执行此操作。


    参考:
    How DEFLATE works, by Antaeus Feldspar

    【讨论】:

    • 您可以使用Z_FIXED 策略在不使用霍夫曼的情况下压缩LZ77。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2011-09-11
    • 1970-01-01
    • 1970-01-01
    • 2015-07-31
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多