Help us understand the problem. What is going on with this article?

PythonにおけるProcessとThread

PythonにおけるProcessとThread

Process

  • Processはプログラムの一つの単位
    • ProcessはThreadを生み出す
    • ThreadはProcessのサブタスクの実行を担う
    • ThreadはProcessの中で扱われ、複数のThreadは同じメモリ空間を共有する
  • Processはプログラムを実行するためにOSから扱われる
  • Processは複数のThreadを持ちうる
  • 2つ以上のProcessは同じPythonコードで同時に実行しうる
  • ProcessはThreadよりオーバーヘッドがかかる
  • Process間の情報共有は、Thread間のものより時間がかかる

Thread

  • ThreadはProcessに内包される小さなProcessのようなもの
  • メモリ空間を共有し、同じ変数を扱う
  • 2つ以上のThreadを同時に同じPythonコードでは実行できない
    • しかし回避策がある

CPU

  • CPUはコンピュータの基本的な演算を管理する
  • CPUは1つもしくは2つ以上のCoreを持ち、複数のcodeを同時に実行することが出来る

GIL

  • 一般的なPythonには、GIL(Global Interpreter Lock)と呼ばれるものがあり、2つ以上のThreadを同時に実行することを認めない
    • なぜならThread-Safeな言語ではないから
  • しかし回避策が存在し、NumpyなどではexternalなcodeをCで実行するなどの策を取っている

Multiple ProcessとMultiple Thread、どちらを選択すればよいのか

  • Multi ProcessはCPUに依存する処理に対して有効に作用する
    • 複数のcoreを有効利用し、GILを無視できるため
  • Multiple ThreadはIO処理、もしくはexternalな処理を含むことに対し有効に作用する
    • しかしCPUに依存する処理に対してはGILがあるため有効ではない

参考コード

  • 記事の「Parallel processing examples」を参照

Gunicornでの例

Gunicornとは

  • PythonでのWSGI/HTTPサーバー
  • DjangoやFlaskなどのWebアプリケーションとnginxやLoad Balancerの間に配置される
  • Unix Pre-Fork Serverを実装している
  • 単一のマスタープロセスを走らせ、子プロセスがWorkerとして動作する
  • マスタープロセスの役割は、設定されたworkerの数が実際に動作しているWorkerの数と一致することを保証すること
    • もしWorkerが止まれば、自身を再ForkしWorkerを新しく生成する
  • Workerの役割はHTTP Requestを捌くこと
  • OS KernelはWorker間をLoad Balancingする役割を果たす

1つ目の並列、Worker

  • それぞれのWorkerはPythonアプリケーションを扱うUnix Process
  • Worker間はメモリを共有していない
  • 推奨Worker数は、CPUの数x2+1
    • デュアルコアなら5つ

2つ目の並列、Thread

  • GunicornはWorkerに複数のThreadを持たせることが出来る
  • Threadは同じWorker内でメモリを共有する
  • 並行リクエストの最大数は、Workerの数xThreadの数
  • 推奨の最大数は、同じくCPUの数x2+1
    • クアッドコアでこのアプローチを選択する場合、Worker:3、Thread:3で9つが理想的

3つ目の並列、Pseudo Threads

  • geventAsyncioは、coroutineで実装されたPseudo Threadsの機能をPythonに提供する
  • Gunicornでもこれを使うことは可能
  • このケースでもCPUの数x2+1が推奨Worker数になる

ユースケース

1. アプリケーションにI/O処理が多い場合

  • 大抵のケースでPseudo Threadsを使うと良いパフォーマンスになる

2. CPU処理が多い場合

  • Worker数を増やすしか方法がない
    • GILによってPseudo ThreadsとThreadのアプローチは使えない
  • 最大並行リクエスト数はCPUの数x2+1であることを理解しなければならない

3. メモリ使用率が高い場合

  • Threadやgthread worker classを使うことが良いパフォーマンスに繋がる

4. もしよくわからない場合

  • Workerの数をとりあえずCPUの数x2+1へ増やすよう設定を変更すればよい

参照

Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
Comments
No comments
Sign up for free and join this conversation.
If you already have a Qiita account
Why do not you register as a user and use Qiita more conveniently?
You need to log in to use this function. Qiita can be used more conveniently after logging in.
You seem to be reading articles frequently this month. Qiita can be used more conveniently after logging in.
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
ユーザーは見つかりませんでした