マルチスレッドとマルチプロセス
マルチスレッドとマルチプロセスは似ているようで違います。マルチプロセス間の実行中の値は、各プロセス間で別になっていますが、マルチスレッドの場合には変数を共用するのでちょっと注意が必要です。
実行環境
- cray xc40
- python 2.7.13
マルチプロセス
ここを参考に
03_multi.py
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 | #!/usr/bin/env python # -*- coding: utf-8 -*- # http://qiita.com/yubais/items/5a9d91fe03fe715b21d0 import multiprocessing as mp import sys L = 40000 proc=int(sys.argv[1]) # 各プロセスが実行する計算 def subcalc(queue, p): subtotal = 0 # iの範囲を設定 ini = L * p / proc fin = L * (p+1) / proc for i in range(ini, fin): for j in range(L): subtotal += i * j # キューにデータを送る queue.put(subtotal) # キューを作成 queue = mp.Queue() # 8個のプロセスを用意 ps=[] for i in range(proc): ps.append(mp.Process(target=subcalc, args=(queue, i))) # すべてを開始 for p in ps: p.start() # キューから結果を回収 total = 0 for i in range(proc): total += queue.get() # キューに値が無い場合は、値が入るまで待機になる print(total) |
36プロセス
03_multi_36.sh
実行スクリプト
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 | #!/bin/sh #PBS -N 03_multi_36 #PBS -j oe #PBS -l select=1:ncpus=36 #PBS -l place=scatter #PBS -q SINGLE if [ "${PBS_O_WORKDIR}" != "" ];then cd ${PBS_O_WORKDIR} fi export OMP_NUM_THREADS=36 . ~/.bashrc APRUN="aprun -n 1 -d $OMP_NUM_THREADS" date $APRUN python 03_multi.py 36 date |
結果
1 2 3 | 2017年 6月 6日 火曜日 09:33:12 JST 639968000400000000 2017年 6月 6日 火曜日 09:33:17 JST |
1プロセス
03_multi_1.sh
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 | #!/bin/sh #PBS -N 03_multi_1 #PBS -j oe #PBS -l select=1:ncpus=1 #PBS -l place=scatter #PBS -q SINGLE if [ "${PBS_O_WORKDIR}" != "" ];then cd ${PBS_O_WORKDIR} fi export OMP_NUM_THREADS=1 . ~/.bashrc APRUN="aprun -n 1 -d $OMP_NUM_THREADS" date $APRUN python 03_multi.py 1 date |
結果
1 2 3 | 2017年 5月 31日 水曜日 10:44:19 JST 639968000400000000 2017年 5月 31日 水曜日 10:45:35 JST |
かなり速度が違います
マルチスレッド
ここを参考
03_multi.py
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 | #!/usr/bin/env python # -*- coding: utf-8 -*- # http://qiita.com/yubais/items/5a9d91fe03fe715b21d0 # http://kaworu.jpn.org/python/Pythonのマルチスレッドプログラミング import threading import sys #http://ja.pymotw.com/2/Queue/ import Queue L = 40000 proc=int(sys.argv[1]) # 各プロセスが実行する計算 def subcalc(queue, p): subtotal = 0 # iの範囲を設定 ini = L * p / proc fin = L * (p+1) / proc for i in range(ini, fin): for j in range(L): subtotal += i * j # キューにデータを送る queue.put(subtotal) # キューを作成 queue = Queue.Queue() # 8個のプロセスを用意 ps=[] for i in range(proc): ps.append(threading.Thread(target=subcalc, args=(queue, i))) # すべてを開始 for p in ps: p.start() p.join() # キューから結果を回収 total = 0 for i in range(proc): total += queue.get() # キューに値が無い場合は、値が入るまで待機になる print(total) |
36プロセス
04_thread_36.sh
実行スクリプト
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 | #!/bin/sh #PBS -N 04_thread_36 #PBS -j oe #PBS -l select=1:ncpus=36 #PBS -l place=scatter #PBS -q SINGLE if [ "${PBS_O_WORKDIR}" != "" ];then cd ${PBS_O_WORKDIR} fi export OMP_NUM_THREADS=36 . ~/.bashrc APRUN="aprun -n 1 -d $OMP_NUM_THREADS" date $APRUN python 04_thread.py 36 date |
結果
1 2 3 | 2017年 6月 6日 火曜日 09:39:57 JST 639968000400000000 2017年 6月 6日 火曜日 09:41:13 JST |
1プロセス
04_thread_1.sh
実行スクリプト
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 | #!/bin/sh #PBS -N 04_thread_1 #PBS -j oe #PBS -l select=1:ncpus=1 #PBS -l place=scatter #PBS -q SINGLE if [ "${PBS_O_WORKDIR}" != "" ];then cd ${PBS_O_WORKDIR} fi export OMP_NUM_THREADS=1 . ~/.bashrc APRUN="aprun -n 1 -d $OMP_NUM_THREADS" date $APRUN python 04_thread.py 1 date |
結果
1 2 3 | 017年 6月 6日 火曜日 09:39:57 JST 639968000400000000 2017年 6月 6日 火曜日 09:41:13 JST |