2016-06-24 4 views
2

Проблема, с которой я столкнулся, - это имя сохраненного файла. Сохраненный файл не имеет имени с исходным/несжатым именем файла. Вместо этого сохраненный файл имеет имя с именем архива (с добавленным расширением «.gz»).Как сжать большой файл в Python?

Ожидаемый результат:
file.txt.gz {имя архива}
.... file.txt {сохраненное имя файла}

Фактический результат:
file.txt.gz {имя архива}
.... file.txt.gz {сохраненное имя файла}

Прочтение документации GZIP (https://docs.python.org/2.7/library/gzip.html) пример кода:

import gzip 
import shutil 
with open('file.txt', 'rb') as f_in, gzip.open('file.txt.gz', 'wb') as f_out: 
    shutil.copyfileobj(f_in, f_out) 

Как получить архив для хранения файла с именем «file.txt» вместо «file.txt.gz»?

+0

Так что вы хотите сохранить сжатый файл в 'file.txt'? перезаписать существующий файл? – oxalorg

+0

Я * считаю, что ОП пытается поставить 'файл.txt' внутри своего '.gz' файла, и они хотят, чтобы имя' file.txt' было именем файла в файле '.gz', но они получают файл' file.txt.gz', который содержит файл 'file.txt.gz'. –

+2

Но теперь, когда я оглядываюсь, не думаю, что gzip - это фактический формат архива, просто сжатие файла. -_- –

ответ

-1

Вы делаете различие между «сохраненным именем файла» и «именем архива», но для сжатия gzip это неправильный способ думать, потому что gzip не является форматом архива, а просто протоколом сжатия.

Когда вы храните файл «gzip», он не (обязательно) запоминает исходное имя файла. Существует только сжатое содержимое исходного файла, в котором вы можете указать любое имя. Существует соглашение, чтобы дать ему то же имя, что и исходный файл, но с добавлением «.gz». В «GZIP» и «Gunzip» утилиты на системах Unix Предположим, если вы только поставить имя файла:

gzip foo.txt 
# now foo.txt has been deleted, and foo.txt.gz exists 
gunzip foo.txt.gz 
# now you have foo.txt back, and foo.txt.gz has been deleted. 

Если переименовать foo.txt.gz в bar.txt.gz, а затем разархивировать, вы будете get 'goo.txt', если вы используете Unix gunzip (но другие утилиты могут делать что-то другое).

Однако вы можете использовать gzip и gunzip в потоковом режиме, и в этом случае они ничего не знают о именах файлов. Gzip действительно касается сжатия и не заботится о именах файлов.

(Редактировать: gzip может хранить имя файла, но в некоторых случаях он не может (если нет оригинального «файла», только данные) и используется ли это, или нет, когда распаковка полностью необязательна).

+1

Я думаю, что это неправильно. Имя файла, скорее всего, сохраняется в заголовке файла gzip, упомянутом в Википедии. Попробуйте переименовать gzip-файл, а затем распаковать его - вы вернете файл с исходным именем, как ранее. Или, по крайней мере, я верну его с программным обеспечением, которое я установил. – brezniczky

+0

@brezniczky правильно с модификацией, «несжатое имя» происходит от имени файла, используемого с 'gzip.open'. Если вы откроете файл 'foo.txt.gz', несжатое имя в заголовке будет' foo.txt', хотя исходный файл можно назвать 'bar.txt'. См. Источник [gzip module] (https://github.com/python/cpython/blob/master/Lib/gzip.py#L229) для логики. –

+0

Вы правы, я не понимал, что gzip действительно хранит оригинальное имя файла. Unix gunzip не использует это при распаковке, если вы не передаете «-N», который не является значением по умолчанию, поэтому на него нельзя положиться. Модули Python могут делать что-то еще, но в целом gzip следует рассматривать как формат сжатия данных, а не формат архива. – spookylukey

1

Вы должны использовать gzip.GzipFile(); стенограмма gzip.open() не будет делать то, что вы хотите.

Quoth the doc:

Когда fileobj не None, то имя файла аргумент используется только для включения в заголовок файла GZIP, который может включать в исходное имя файла несжатого файла , По умолчанию используется имя файла fileobj, если оно распознано; в противном случае по умолчанию используется пустая строка, и в этом случае исходное имя файла не включается в заголовок.

Попробуйте это:

import gzip 
import shutil 
with open('file.txt', 'rb') as f_in: 
    with open('file.txt.gz', 'wb') as f_out: 
     with gzip.GzipFile('file.txt', 'wb', fileobj=f_out) as f_out: 
      shutil.copyfileobj(f_in, f_out)