2016-08-15 11 views
1

Python 3.5を使用してgzipファイルから圧縮されていないファイルを書き込むメモリ効率的な方法

私はgzipファイルを解凍して別のファイルに書き出しています。メモリの問題のうちに見た後、私はgzipのモジュールのドキュメントに例を見つける:

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

これは圧縮を行い、そして私が解凍したいので、私は与えて、私はちょうどパターンを逆にすることができていること、それを取ります

with gzip.open(zipped_file, 'rb') as zin, open(unzipped_file, 'wb') as wout: 
    wout.write(zin.read()) 

どちらか私は最後の藁の上に置かれ、または私は、ファイルは次のように行動するだろうと信じにナイーブだった:私の質問は、なぜ私は、次のとメモリのトラブルにもらったのさ

with open(unzipped_file, 'wb') as f_out, gzip.open(zipped_file, 'rb') as f_in: 
    shutil.copyfileobj(f_in, f_out) 

解凍プロセスをストリームし、メモリをほとんど使用しません。これらの2つの方法は同等であるべきですか?

+0

'shutil.copyfileObj'メソッドのコードを見ることをお勧めします。 –

+0

"ファイルがジェネレータのように振舞うと信じていたのは純粋だった*" - それだけです。あなたはあなた自身の質問に答えました。 –

答えて

2

ここにはshutil.copyfileObjメソッドがあります。

def copyfileobj(fsrc, fdst, length=16*1024): 
    """copy data from file-like object fsrc to file-like object fdst""" 
    while 1: 
     buf = fsrc.read(length) 
     if not buf: 
      break 
     fdst.write(buf) 

長さが16×1024のチャンクでファイルを読み取ります。そしてプロセスを逆にしようとすると、メモリに読み込まれてメモリの問題に陥るファイルのサイズを考慮していません。代わりに、私はこれをテストし、以前の回答に基づいて空腹(ナイーブ)メモリ

import gzip 
with gzip.open(zipped_file, 'rb') as zin, open(unzipped_file, 'wb') as wout: 
    wout.write(zin.read()) 

+0

これは私が示したように本質的に複製するのではなく、よりクリーンな解決策です。 – mohawkTrail

0

:4.8gのファイルに検証

import gzip 
block_size = 64*1024 
with gzip.open(zipped_file, 'rb') as zin, open(unzipped_file, 'wb') as wout: 
while True: 
    uncompressed_block = zin.read(block_size) 
    if not uncompressed_block: 
     break 
    wout.write(uncompressed_block) 

+0

私はこのようにしなければならないと感じています。誰もがリンクしていますか? – mohawkTrail

+0

@Vinitによる解決策とJean-Francoisの言及が最高です。 – mohawkTrail