【问题标题】:Compressing large string in ruby在红宝石中压缩大字符串
【发布时间】:2013-07-26 18:56:09
【问题描述】:

我有一个 Web 应用程序(ruby on rails),它发送一些 YAML 作为隐藏输入字段的值。

现在我想减小发送到浏览器的文本的大小。传输最少数据的最有效的无损压缩形式是什么?我可以在服务器端产生额外的压缩和解压缩成本。

【问题讨论】:

    标签: ruby compression


    【解决方案1】:

    您可以使用 ruby​​ 核心中的 zlib 实现来输入/删除数据:

    require "zlib"
    data = "some long yaml string" * 100
    compressed_data = Zlib::Deflate.deflate(data)
    #=> "x\x9C+\xCE\xCFMU\xC8\xC9\xCFKW\xA8L\xCC\xCDQ(.)\xCA\xCCK/\x1E\x15\x1C\x15\x1C\x15\x1C\x15\x1C\x15\x1C\x15\x1C\x15\x1C\x15D\x15\x04\x00\xB3G%\xA6"
    

    您应该对压缩数据进行 base64 编码以使其可打印:

    require 'base64'
    encoded_data = Base64.encode64 compressed_data
    #=> "eJwrzs9NVcjJz0tXqEzMzVEoLinKzEsvHhUcFRwVHBUcFRwVHBUcFUQVBACz\nRyWm\n"
    

    稍后,在客户端,您可能会使用pako(到 javascript 的 zlib 端口)来取回您的数据。 This answer 可能会帮助您实现 JS 部分。

    为了让您了解其效果如何,以下是示例字符串的大小:

    data.size            # 2100
    compressed_data.size #   48
    encoded_data.size    #   66
    

    在客户端压缩并在服务器上膨胀时,反之亦然。

    Zlib::Inflate.inflate(Base64.decode64(encoded_data))
    #=> "some long yaml stringsome long yaml str ... (shortened, as the string is long :)
    

    免责声明:

    • ruby zlib 实现应该与 pako 实现兼容。但我没试过。
    • 关于字符串大小的数字有点作弊。 Zlib 在这里真的很有效,因为字符串重复很多。现实生活中的数据通常不会重复太多。

    【讨论】:

    • 几天前我无意中对此投了反对票,因为我不记得这样做了。如果你愿意,请进行编辑,以便我可以收回我意外的否决票:(
    • @Krule 感谢您的友善。首先我不确定我是否找到了有用的更新,但后来我偶然发现了 pako,它(似乎)是一个比 zlib 更好的 zlib js 库。所以感谢提醒再次查看我的答案,我实际上可以改进它:)
    • 请注意Zlib::Deflate.deflate 的输出与gzip 命令行实用程序生成的格式不兼容,并且不会被gunzip 接受,它需要在压缩之前有一些头数据内容。如果您想使用gunzip 读取输出,以下代码将很有用:Zlib::Deflate.new(nil, 31).deflate(data, Zlib::FINISH)
    • 这非常有效,因为示例数据集多次重复测试,在其他示例中效率较低。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2010-11-29
    • 1970-01-01
    • 2014-02-11
    • 2011-01-21
    • 2010-09-25
    • 1970-01-01
    相关资源
    最近更新 更多