2019-11-21目次マルチスレッドワーカーを使う場合デーモンスレッドを使わない場合キューを使わない場合クラスを使う場合マルチスレッドで並行処理させちゃう参照マルチスレッドPythonでマルチスレッドを使うには大きく分けて2つのパターンがあります。それは以下の通りです。ワーカーを使うクラスを使うこれらの使い方を簡単に紹介します。ワーカーを使う場合ワーカーとは何なのかと言う、スレッドで動作させるエントリーポイントとなる関数のことです。スレッドを作る時にこの関数をスレッドに指定しておくと、スレッドを起動したときその関数から処理がスタートします。関数が終了すると起動したスレッドも終了します。ワーカーと別のスレッドでデータを共有したい時の1つの手段としてqueueモジュールを使う方法があります。queue.Queueは同期キュークラスと呼ばれ、こういった並行処理でデータをやり取りするときに使われます。↓がサンプルスクリプトです。main()↑のコードを実行すると↓のような結果になります。2.5040030479431152↑の例ではまずmain関数内でndatasを使ってdata_qを初期化しています。このdata_qはQueueです。それからnthreadsを使ってworker関数をターゲットにしてスレッドを複数作成し、各スレッドをスタートさせています。この各スレッドはdata_qのデータをそれぞれ処理していきます。ここが並行処理になってますね。それからdata_q.join()でキューの処理が完了するのを待ちます。各スレッドがそれぞれの仕事を処理して、キューの仕事が空になったら処理が完了します。このとき、スレッドの作成時にスレッドのdaemon属性をTrueにしておくのを忘れないようにしましょう。することでスレッドはデーモンスレッドになります。デーモンスレッドとはユーザースレッドがすべて終了すると、自動的に終了する性質を持ったスレッドです。このdaemon属性はデフォルトではFalseですが、Falseのときスレッドはユーザースレッドになります。メインスレッドが終了したら起動したデーモンスレッドも勝手に終了してくれるということですね。デーモンスレッドを使わない場合もちろんデーモンスレッドを使わずに書くことも出来ます。main()↑のコードを実行すると↓のような結果になります。doneデーモンスレッドを使った場合はスレッドを起動しっぱなしでしたが、スレッドのdaemon属性をTrueにしない場合は↑のようにスレッドをjoinして、スレッドの終了を待機するのがマナーです。Queueのgetメソッドは内部でスレッドをロックしているので、timeout引数にそのロック時間を指定します。↑の例では3秒間ロックして、データを取得できなければEmpty例外を発生させてスレッドを終了するようにしています。キューが空になる又はEmpty例外が発生した場合、スレッドは終了します。デーモンスレッドは起動しっぱなしでプログラム終了時に勝手に回収されるのを期待するスレッドなので、ゲームなどではこっちのユーザースレッドのほうが需要が高いかもしれません。キューを使わない場合もちろんキューを使わずに書くことも出来ます。↓はbufferというグローバル変数の文字列にランダムな文字を並行処理的に追加していくスクリプトです。main()↑のコードを実行すると↓のような結果になります。done各スレッドは文字列bufferが20字以上になったらスレッドを終了します。buffer_lockという変数はアクセスしたい変数を競合スレッドから保護する変数です。with文にこのロック変数を渡すとwith文に入ったときにロック変数をロックします。このあいだ、競合スレッドは同じロック変数をロックしてbufferにアクセスしようとしますが、ロックされているのでアクセス待ちの状態になります。従って1つのスレッドがbufferにアクセスしている時に、他のスレッドが破壊的な変更などを行う心配がなくなります。Queueに比べるとロック変数を使った処理のほうが簡単かもしれませんが、人によるかもしれません。ちなみにロック変数を使った場合、簡単にロック地獄になります。むずかしい設計になりますので気をつけましょう。クラスを使う場合クラスを使う場合はthreadingモジュールのThreadクラスを任意のクラスに継承させます。safe_print('done')↑のコードを実行すると↓のような結果になります。secdoneこのスクリプトはスレッド間のメッセージの送受信をシミュレートしていますが、実際にはメッセージの送受信は行っておらず、一定時間スリープしてprintしているだけです。Threadクラスを継承するとstartメソッドやjoinメソッドを使うことが出来るようになります。startメソッドを呼び出すと内部でrunメソッドが呼ばれます。そのためrunメソッドをオーバーライドしておくとスレッド開始時の処理を定義することが出来ます。あとはjoinメソッドを使えばスレッドの終了を待機することが出来ます。マルチスレッドで並行処理させちゃうこのようにマルチスレッドを使うと簡単に並行処理を実現することが出来ます。音楽聞きながら絵を描いてコーヒーを飲むという複雑な動作が、パソコンにもできるということですね。これは厳密には並列処理だと思いますが。こまけぇこたぁいいんだよはい。今回は以上になります。次へ名前:投稿者名です。64字以内で入力してください。Eメール:必要な場合はEメールアドレスを入力してください(全体に公開されます)。内容:投稿する内容です。2019NARUPORTnarupoのブログおみくじ小説Webツール。