「労働者が自分の仕事をうまくやりたいなら、まず自分の道具を研ぎ澄まさなければなりません。」 - 孔子、「論語。陸霊公」
表紙 > プログラミング > Python のマルチプロセッシング プールでキーボード割り込みを処理するにはどうすればよいですか?

Python のマルチプロセッシング プールでキーボード割り込みを処理するにはどうすればよいですか?

2024 年 12 月 22 日に公開
ブラウズ:885

How to Handle Keyboard Interrupts in Python\'s Multiprocessing Pool?

Python のマルチプロセッシング プールでのキーボード割り込みの処理

Python のマルチプロセッシング モジュールでは、Pool クラスは複数のプロセスにタスクを分散する便利な方法を提供します。ただし、コード スニペット:

from multiprocessing import Pool
from time import sleep
from sys import exit

def slowly_square(i):
    sleep(1)
    return i*i

def go():
    pool = Pool(8)
    try:
        results = pool.map(slowly_square, range(40))
    except KeyboardInterrupt:
        # **** THIS PART NEVER EXECUTES. ****
        pool.terminate()
        print "You cancelled the program!"
        sys.exit(1)
    print "\nFinally, here are the results: ", results

if __name__ == "__main__":
    go()

このコードを実行するときに Ctrl C を押してもクリーンアップ プロセスはトリガーされず、サブプロセスは無制限に実行されたままになります。この問題に対処するには、次の回避策を検討してください。

コード内で確認された動作は、Python のバグの結果です。 threading.Condition.wait() で条件を待機している場合、KeyboardInterrupt は送信されません。 Pool.map() は内部で条件待機を使用するため、割り込みは決して受信されません。

解決策は、タイムアウトを指定できる Pool.map_async() を使用することです。十分に長いタイムアウト (例: 9999999) を設定することで、適切な時間内に割り込みがトリガーされることを保証できます。

したがって、 replace:

    results = pool.map(slowly_square, range(40))

with:

    results = pool.map_async(slowly_square, range(40)).get(9999999)

この回避策は、マルチプロセス プールで KeyboardInterrupt イベントを適切に処理する方法を提供し、ユーザーがプログラムをキャンセルしたときにすべてのサブプロセスを終了できるようにします。 .

リリースステートメント この記事は次の場所に転載されています: 1729576640 権利侵害がある場合は、[email protected] に連絡して削除してください。
最新のチュートリアル もっと>

免責事項: 提供されるすべてのリソースの一部はインターネットからのものです。お客様の著作権またはその他の権利および利益の侵害がある場合は、詳細な理由を説明し、著作権または権利および利益の証拠を提出して、電子メール [email protected] に送信してください。 できるだけ早く対応させていただきます。

Copyright© 2022 湘ICP备2022001581号-3