Zlib в Ruby, чтобы распаковать .gz - PullRequest
7 голосов
/ 03 июля 2010

У меня есть файл .gz, который содержит документ XML. Кто-нибудь знает, как правильно использовать Zlib? Пока у меня есть следующий код:

require 'zlib'
Zlib::GzipReader.open('PRIDE_Exp_Complete_Ac_1015.xml.gz') { |gz|
    g = File.new("PRIDE_Exp_Complete_Ac_1015.xml", "w")
      g.write(gz)
      g.close()
}

Но это создает пустой XML-документ. Кто-нибудь знает, как мне правильно это сделать?

Ответы [ 2 ]

23 голосов
/ 03 июля 2010

Zlib::GzipReader работает так же, как большинство IO -подобных классов в Ruby. У вас есть вызов open, и когда вы передадите ему блок, он получит объект, подобный IO. Подумайте об этом, это удобный способ сделать что-то с файлом или ресурсом на время блока.

Но это означает, что в вашем примере gz является IO -подобным объектом, а не фактически содержимым gzip-файла, как вы ожидаете. Вам все еще нужно read от него, чтобы добраться до этого. Самое простое исправление будет тогда:

g.write(gz.read)

Обратите внимание, что это прочитает все содержимое несжатого gzip в память.

Если все, что вы действительно делаете, это копирование из одного файла в другой, вы можете использовать более эффективный метод IO.copy_stream. Ваш пример может выглядеть так:

Zlib::GzipReader.open('PRIDE_Exp_Complete_Ac_1015.xml.gz') do | input_stream |
  File.open("PRIDE_Exp_Complete_Ac_1015.xml", "w") do |output_stream|
    IO.copy_stream(input_stream, output_stream)
  end
end

За кулисами будет пытаться использовать системный вызов sendfile, доступный в некоторых конкретных ситуациях в Linux. В противном случае он будет выполнять копирование в быстрых блоках кода C размером 16 КБ за раз. Это я узнал из исходного кода Ruby 1.9.1.

2 голосов
/ 29 декабря 2011

Вот Ruby с одной строкой (cd .git / first и укажите путь к любому объекту):

ruby -rzlib -e 'print Zlib::Inflate.new.inflate(STDIN.read)' < ./74/c757240ec596063af8cd273ebd9f67073e1208
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...