スレッドプール
事前に生成したスレッドを再利用し、スレッド生成のオーバーヘッドを削減する並行処理パターン
スレッドプールとは
スレッドプールは、事前に一定数のスレッドを生成しておき、タスクが到着するとプールからスレッドを割り当てて実行し、完了後にスレッドをプールに返却するパターンである。リクエストごとにスレッドを生成・破棄するオーバーヘッドを回避し、同時実行数を制御する。
仕組み
スレッドプールは一定数のスレッドを事前に生成しておき、タスクキューからタスクを取り出して実行する。スレッドがタスクを完了すると、次のタスクをキューから取り出す。スレッドの生成・破棄のオーバーヘッドを回避し、同時実行数を制御できる。
↓ ↓ ↓
スレッドプール: [Thread1] [Thread2] [Thread3] ← 3 スレッド
↓ ↓ ↓
Task1 Task2 Task3 を実行中
完了 → Task4 を実行
Node.js の Worker Thread プール
Node.js はシングルスレッドだが、worker_threads でスレッドプールを実装できる。piscina ライブラリが広く使われている。
import Piscina from 'piscina';
const pool = new Piscina({
filename: './worker.js',
maxThreads: 4, // プールサイズ
});
// タスクをプールに投入
const results = await Promise.all(
images.map(img => pool.run({ path: img, width: 800 }))
);
libuv のスレッドプール
Node.js の内部では、libuv がスレッドプール (デフォルト 4 スレッド) を使って、ファイル I/O、DNS 解決、暗号化処理を非同期に実行している。
# libuv のスレッドプールサイズを変更
UV_THREADPOOL_SIZE=8 node app.js
ファイル I/O が多いアプリケーションでは、デフォルトの 4 スレッドがボトルネックになることがある。
プールサイズの設計
プールサイズの設計を以下にまとめる。
| ワークロード | 推奨サイズ | 理由 |
|---|---|---|
| CPU バウンド | CPU コア数 | コア数以上にしてもコンテキストスイッチが増えるだけ |
| I/O バウンド | CPU コア数 × 2〜4 | I/O 待ちの間に他のスレッドが実行できる |
| 混合 | 計測して調整 | プロファイリングで最適値を決定 |
DB コネクションプールとの関係
DB コネクションプールはスレッドプールの応用だ。TCP 接続の確立コスト (ハンドシェイク、認証) を回避し、接続を再利用する。Lambda では RDS Proxy がコネクションプーリングを提供する。
Java の ExecutorService
Java の ExecutorService のコード例を示す。
ExecutorService pool = Executors.newFixedThreadPool(4);
Future<String> future = pool.submit(() -> {
return processData();
});
String result = future.get(); // 結果を待つ
pool.shutdown();
現場での応用を知るには関連書籍も役立つ。
この記事は役に立ちましたか?
関連用語
オブジェクトプールパターン
生成コストの高いオブジェクトを事前に確保してプールし、再利用することでパフォーマンスを向上させるパターン
Worker Threads
Node.js で CPU 集約的な処理をメインスレッドをブロックせずに別スレッドで実行する仕組み
並行処理
複数のタスクを論理的に同時に進行させるプログラミング手法で、システムのスループットと応答性を向上させる
goroutine
Go の軽量スレッドで、数百万の並行処理を低コストで実現する
イベントループ
Node.js のシングルスレッドで非同期 I/O を実現する実行モデル
Go
Google が開発したシンプルで高速なコンパイル言語で、goroutine による軽量な並行処理が特徴
関連する記事
あの有名 OSS のコードは、この本の影響を受けている
広く使われているオープンソースソフトウェアの設計には、特定の技術書の影響が色濃く反映されています。OSS のコードと技術書の関係を知ると、両方の理解が深まります。
コードを「書く力」と「読む力」は別物 - 読解力を鍛える技術書の使い方
プログラミングの「書く力」ばかり鍛えていませんか。他人のコードを正確に読み解く力は、技術書を使って意識的に鍛えられます。読解力を高める具体的な方法を紹介。
1 万行のコードより 1 冊の設計書が勝つ場面
大量のコードを書く力と、適切な設計を選ぶ力は別物です。コード量では解決できない問題に直面したとき、設計の知識がどう効くのかを具体例で解説します。