このbz2 decompress code(解凍コード)の難点は、解凍までに冗談と思えるくらい非常に時間がかかるということで、つまり、ある意味で全く使い物にならないということだ。
bz2ファイルの解凍後のサイズは、gzipファイルのようにアーカイブの最後の方の4バイトに書かれてはいないので、以下のように最初から最後までseekすることで解凍後のtotal_sizeサイズを得ることができる。従って、total_sizeを割り出すまでにかなりの時間を要する。
1 2 3 4 | f= bz2.BZ2File(fname, 'rb') f.seek(0, os.SEEK_END) total_size = f.tell() f.close() |
progress barは前回同様、以下のようにしてtqdmを使えば簡単に作れる
pbar = tqdm(total=total_size, unit='B', unit_scale=True, unit_divisor=1024)
後はbz2 moduleでファイルを読み出して別ファイルに書き込めばbz2を解凍できる。
最終的なコードは、不格好ながら、以下のような簡単なものに仕上がる。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 | from tqdm import tqdm import bz2 import os.path import os fname = "enwiki-latest-pages-articles1.xml-p10p30302.bz2" f= bz2.BZ2File(fname, 'rb') f.seek(0, os.SEEK_END) total_size = f.tell() f.close() store_path = os.path.splitext(fname)[0] pbar = tqdm(total=total_size, unit='B', unit_scale=True, unit_divisor=1024) fr = bz2.open(fname, 'rb') with open(store_path, 'wb') as fw: for d in fr: w = fw.write(d) pbar.update(w) |
解凍後のスクリーンショットはこんな感じだ。
解凍後のサイズが10Gとかだと、解凍までに1時間くらいかかる可能性がある。実際にbz2ファイルを解凍するなら以下のようにして解凍するのがいいだろう。
1 2 3 4 5 | import bz2,shutil with bz2.BZ2File("enwiki-latest-pages-articles1.xml-p10p30302.bz2") as fr: with open("wikidump","wb") as fw: shutil.copyfileobj(fr,fw) # read by 1MB chunks |
これだと1分弱で解凍作業が終了するので、tqdmを使うより10倍近くも高速だ。
参考サイトhttps://stackoverflow.com/スポンサーリンク
スポンサーリンク