ぐいぐい 入れると ぃい感じ GIL回避
ロックさせないように自由に子プロセス造ってしまうと、思ったようにシンクロしないから、せっかく自由になった子プロセスをロックすれば良いよ。と言うのを見つけたけど、それは本末転倒だろうと思った。
http://docs.python.org/dev/library/multiprocessing.html#module-multiprocessing
↑参考にしたところ
これがそのソース
from multiprocessing import Process, Lock def f(l, i): l.acquire() print 'hello world', i l.release() if __name__ == '__main__': lock = Lock() for num in range(10): Process(target=f, args=(lock, num)).start()
試しに、ロックなしでやってみた。10回じゃ全然正常に動くのでちょっと多めに回してみる。ただLockを外して1000回回しただけ、ソース
from multiprocessing import Process, Lock g_num = 0 def f(i): global g_num #l.acquire() g_num = i print 'hello world', i, g_num #l.release() if __name__ == '__main__': for num in range(1000): Process(target=f, args=(num,)).start()
↓その結果
hello world 0 0 hello world 1 1 hello world 2 2 hello world 3 3 hello world 4 4 hello world 5 5 省略 hello world 114 114 hello world 113 113 hello worldhello world 115 115 116 116 hello world 117 117 省略 hello world 133 133 hello worldhello world 135 135 134 134 hello world 136 136 省略 hello world 420 420 hello world hello world422 422 421 421 hello world 423 423 省略 hello world 910 910 hello world 912 hello world 913 913 912 hello world 914 914
順番が入れ替ったり、なんか変なところで割込んで来たり。こうやってプリントすると、色々変なことになるのが非常にわかりやすい。めっちゃフリーダムな感じ。なんで順番が入れ替るのかが不思議でしょうがないな、確実に順番に頼んでるはずなのに・・(深い追いしても判りそうにないので、そこには目を向けないでおく、覚えてやがれ!)
このままだと、無駄に正常じゃ無くしただけで全然嬉しくない。実際に使いたい場面は、処理Aを子プロセスにして処理Bに取りかかると言うことをしたい。そこで、呼ぶ部分も子プロセスにしてしまう。その後、別に普通の処理をさせてみる(その中でsleepするような事もさせてみる)Process使わなかったら普通全体がスリープしちゃうし、そもそも、処理Aが終らないと処理Bが始らない。ソース↓
# coding:utf-8 from multiprocessing import Process, Lock import time g_num = 0 def f(i, l): l.acquire() global g_num g_num = i print 'hello world', i, g_num l.release() def lopy(lcnt, lock): for num in range(lcnt): Process(target=f, args=(num,lock)).start() if __name__ == '__main__': lock = Lock() Process(target=lopy, args=(100,lock)).start() for i in range(10): print 123 time.sleep(0.03)
その結果
>>> mp_01.py 123 hello world 0 0 hello world 1 1 hello world 2 2 hello world 4 4 hello world 3 3 hello world 6 6 123 hello world 7 7 hello world 8 8 hello world 5 5 hello world 9 9 hello world 10 10 hello world 11 11 hello world 12 12 123 hello world 13 13 hello world 14 14 hello world 15 15 hello world 16 16 hello world 17 17 123 hello world 19 19 hello world 20 20 hello world 18 18 hello world 21 21 hello world 22 22 hello world 23 23 hello world 24 24 123 hello world 25 25 hello world 27 27 hello world 26 26 hello world 28 28 hello world 29 29 123 123 123 123 123
めっちゃ良い感じに動いてる。
ロックも使うように戻したので 順番が狂うこともない。happy!
ロックしてもグローバルでロックされる訳じゃなかったのね、オレ勘違いしてたね。というオチ。情けない。でも、やってみて分ったので楽しかった。楽しいと思ったのはつかの間・・・
所々に書いてある、g_numというグローバルな変数でデータが壊れるかどうか見てみたかったけど、グローバルの変数にアクセスしてないぽい。さらにreturnも出来ないので、データの返しが全然出来ない・・・
受渡しの「渡し」は出来てるけど「受け」が出来ない。
次は、データの共有方法を試す
ps:人間と最中限したい!