Pythonから約8000個のファイルを外部コマンドで起動したい。すべてのファイルは他のファイルとは独立して処理されます。唯一の制約は、すべてのファイルが処理された後に実行を続けることです。私は2つの論理コア(multiprocessing.cpu_count()
が8を返します)を持つ4つの物理コアを持っています。私の考えは、8つのコアのうちの4つで実行される4つの並列独立プロセスのプールを使用することでした。その間、私のマシンは使えるはずです。何千ものファイルを外部コマンドで多重処理する
import multiprocessing
import subprocess
import os
from multiprocessing.pool import ThreadPool
def process_files(input_dir, output_dir, option):
pool = ThreadPool(multiprocessing.cpu_count()/2)
for filename in os.listdir(input_dir): # about 8000 files
f_in = os.path.join(input_dir, filename)
f_out = os.path.join(output_dir, filename)
cmd = ['molconvert', option, f_in, '-o', f_out]
pool.apply_async(subprocess.Popen, (cmd,))
pool.close()
pool.join()
def main():
process_files('dir1', 'dir2', 'mol:H')
do_some_stuff('dir2')
process_files('dir2', 'dir3', 'mol:a')
do_more_stuff('dir3')
シーケンシャル治療は、100個のファイルのバッチのために120秒をとります。ここでは
は、私が何をしてきたのです。上記で概説したマルチプロセッシングバージョン(機能process_files
)は、バッチに対して20秒しかかかりません。しかし、私がprocess_files
を8000個のファイル全体で実行すると、PCがハングし、1時間後にフリーズしません。
私の質問は以下のとおりです。
1)私は)ThreadPool
が正確には、ここでmultiprocessing.cpu_count()/2
プロセスのプロセスのプールを(初期化することになっていると思いました。しかし私のコンピュータは8000のファイルにぶら下がっているが、100ではなく、プールのサイズが考慮されていないことを示唆している。それか、私は何か間違ったことをしています。あなたは説明できますか?
2)Pythonで独立したプロセスを起動するには、それぞれが外部コマンドを起動する必要があり、すべてのリソースが処理で取り込まれないようにするのが正しい方法ですか?
@larsks( 'ThreadPool'は' apply_async'とサブプロセス 'call's)で提案されたソリューションと@Roland Smith(' Popen'オブジェクトを使った手動プール管理)を比較しました。私のベンチマークでは、 'ThreadPool'の方が実際の方が高速です。両方とも非常にありがとう! – user3638629