Python で並列処理を実行する

Najwa Riyaz 2023年1月30日
  1. Python で処理プールとそのメソッドを使用してマルチプロセッシングを実行する
  2. Python で apply_async() 関数を使用してマルチプロセッシングを実行する
  3. Python で map() および map_sync() 関数を使用してマルチプロセッシングを実行する
Python で並列処理を実行する

この記事では、Python で複数のプロセスを並行して実行する方法について説明します。

Python で処理プールとそのメソッドを使用してマルチプロセッシングを実行する

Python でマルチプロセッシングを実行するには、次の手順を実行します。

  • まず、multiprocessing モジュールをインポートします。
  • Pool クラスを使用して、Python 処理プールを定義します。このプールは、ワーカープロセスのプールを表します。以下のコードスニペットを例として取り上げます。
Pool(processes=n)

したがって、Pool クラスでは、n 個のプロセスを同時に実行できます。このクラスには、プールのワーカープロセスへのタスクの委任を可能にするメソッドが含まれています。

以下は、Pool クラスのメソッドの一部です。

  • Pool.map() - プールのこのブロックメソッドを使用して、結果の準備ができるまでブロックします。このメソッドは、関連付けられた反復可能なものをいくつかのチャンクに切り刻みます。次に、チャンクを個別のタスクとしてプロセスプールに送信します。

  • Pool クラスの次の非ブロッキングメソッドを使用して、プロセスを一度に同時に送信します。get() メソッドを使用して、関数の結果を取得します。

  • Pool.apply_async()

  • Pool.map_async()

マシンがマルチプロセッシングのために処理できるプロセスの数を決定するには、デバイスにあるプロセッサの数を知っている必要があります。次のコードを使用してこれを確認できます。

import multiprocessing as mp

print("Number of processors: ", mp.cpu_count())

出力:

Number of processors:  4

Python で apply_async() 関数を使用してマルチプロセッシングを実行する

これは、0〜9 の数値の範囲の二乗を決定しながら、Python の処理プールを使用したマルチプロセッシングを示す例です。

ここでは、オプションのプロセスワーカーの名前も出力していることに注意してください。

from multiprocessing import Pool
from multiprocessing import Process, current_process
import time
from time import sleep
import random


def fnc_square(x):
    print(current_process().name)
    return x * x


if __name__ == "__main__":
    pool = Pool(processes=4)
    result = pool.apply_async(fnc_square, [6])
    print(result.get(timeout=1))
    print(pool.map(fnc_square, range(10)))

出力:

SpawnPoolWorker-1
36
SpawnPoolWorker-2
SpawnPoolWorker-1
SpawnPoolWorker-2
SpawnPoolWorker-1
SpawnPoolWorker-2
SpawnPoolWorker-1
SpawnPoolWorker-2
SpawnPoolWorker-1
SpawnPoolWorker-2
SpawnPoolWorker-1
[0, 1, 4, 9, 16, 25, 36, 49, 64, 81]

Python で map() および map_sync() 関数を使用してマルチプロセッシングを実行する

map_async 関数は非ブロッキングですが、map 関数はブロッキングです。以下は、これら 2つのコマンドの違いを示す例です。

from multiprocessing import Pool
import time


def f(x):
    print(x * x)


if __name__ == "__main__":
    pool = Pool(processes=1)
    pool.map(f, range(10))
    r = pool.map_async(f, range(10))
    print("First print")
    print("Second print")
    r.wait()
    print("Third print")

ここで、pool.map() 関数が 10 回の操作呼び出しが完了するのを待つことがわかります。したがって、結果が順番に出力されていることがわかります。

さらに、pool.map_async() は 10 個の関数呼び出しを非同期で実行します。r.wait() 関数が呼び出されると、実行のためにプロセッサをブロックします。したがって、出力では、出力メッセージは First printSecond print の間に表示されますが、Third print は常に最後になります。

出力:

0
1
4
9
16
25
36
49
64
81
First print
Second print
0
1
4
9
16
25
36
49
64
81
Third print

関連記事 - Python Process