プロセスとスレッド
プロセスは独立したメモリ空間を持つ“実行中のプログラム”、スレッドはその中でメモリを共有しながら走る“実行単位”。隔離を取るか軽さ・共有を取るかで使い分ける。
- 1.プロセスは 独立した仮想メモリ空間を持つ実行単位。互いに隔離され、生成・切替コストは重い。
- 2.スレッドは プロセス内の実行単位で、コード/データ/ヒープを共有。生成・切替が軽い代わりに干渉しやすい。
- 3.使い分け:堅牢性・隔離なら マルチプロセス、軽量な並行・データ共有なら マルチスレッド。
プロセス:独立したメモリ空間を持つ実行単位
プロセスは、プログラム(ディスク上の静的なファイル)を OS が読み込んで 実行状態にしたもの。プロセスごとに OS が次のような独立した資源を割り当てます。
- 仮想アドレス空間:コード(text)・データ・ヒープ・スタックを含む、そのプロセス専用のメモリ
- ファイルディスクリプタ:開いているファイルやソケットの一覧
- PID(プロセスID)・権限・環境変数 など
重要なのは、各プロセスが 自分専用の仮想メモリ を持つこと。プロセス A から見えるアドレス 0x1000 と、プロセス B の 0x1000 は 別の物理メモリ を指します(仮想記憶の働き。詳しくは /os/virtual-memory/)。
→ あるプロセスがバグでメモリを壊しても、他のプロセスには波及しにくい。この 隔離 が堅牢性の源です。
スレッド:プロセス内でメモリを共有する実行単位
スレッドは、プロセスの中で CPU に実行される流れ そのものです。同じプロセスのスレッドどうしは、多くの資源を 共有 します。
プロセス(1つのアドレス空間)
├─ コード(text) ─┐
├─ データ ├─ スレッド間で共有
├─ ヒープ ┘
├─ スレッド1 → 専用スタック + レジスタ + PC
└─ スレッド2 → 専用スタック + レジスタ + PC
- 共有するもの:コード・グローバル/静的データ・ヒープ・開いているファイル
- スレッドごとに固有のもの:スタック・レジスタ・プログラムカウンタ(PC)
つまりスレッドは「どこを実行中か(PC)」と「ローカル変数や呼び出し履歴(スタック)」だけを個別に持ち、残りは共有します。だから データの受け渡しが速く・軽い 一方で、共有メモリへの同時アクセスで簡単に壊れます(→ /os/concurrency-control/)。
比較表
| 観点 | プロセス | スレッド |
|---|---|---|
| メモリ空間 | 独立(専用の仮想アドレス空間) | プロセス内で共有 |
| 隔離性 | 高い(片方が落ちても波及しにくい) | 低い(1つのクラッシュで全体が落ちうる) |
| 生成コスト | 重い(空間・資源を確保) | 軽い(スタック等のみ確保) |
| 切替コスト | 重い(アドレス空間ごと切替・キャッシュ無効化) | 軽い(同一空間内で切替) |
| データ共有 | 明示的なIPCが必要 | 変数を直接共有できる |
| 主な用途 | 隔離・堅牢性が要るとき | 軽量な並行・密なデータ共有 |
コンテキストスイッチ:切り替えのコスト
CPU コアは一度に1つの実行単位しか走らせられないため、OS は短い時間ごとに実行対象を切り替えます。これが コンテキストスイッチ です(切り替えの判断は /os/scheduling/ が行います)。
切り替え時に OS は、走っていたスレッドの レジスタ・PC・スタックポインタ を保存し、次のスレッドのそれを復元します。ここで プロセスをまたぐ 切替は割高になります。
同じプロセス内のスレッド切替は、共有しているアドレス空間をそのまま使えます。しかし 別プロセス への切替では、仮想アドレス空間(ページテーブル)の切替 が伴い、TLB やキャッシュの内容が無効化されがちです。結果としてプロセス切替はスレッド切替より高コストになります。
並行と並列:似て非なるもの
「同時に動く」という言葉には2つの意味があり、混同されがちです。
- 並行(concurrency):複数のタスクを 見かけ上同時 に進める。1コアでも、高速に切り替えれば実現できる(時分割)
- 並列(parallelism):複数のタスクを 物理的に同時 に実行する。複数のコア(または CPU)が必要
並行(1コア): A → B → A → B → A (素早く交代して進める)
並列(2コア): コア1: A A A A
コア2: B B B B (本当に同時に走る)
スレッドを増やしても、コア数を超えた分は 並列ではなく並行(交代実行)になります。さらに CPU を使い切る計算処理(CPUバウンド)では、言語によっては排他制御(例:一部処理系のグローバルロック)が並列実行を妨げることもあります。「多くのスレッド=速い」ではなく、ワークロードとコア数次第 です。
マルチプロセス vs マルチスレッド
並行・並列を実現する手段として、複数プロセスで攻めるか、複数スレッドで攻めるかを選びます。
- マルチプロセス:プロセスを複数立てる。隔離が強く堅牢(1つが落ちても他は生存)。ただし生成・切替が重く、データ共有には IPC(パイプ・共有メモリ・ソケット等)が必要
- マルチスレッド:1プロセス内でスレッドを複数立てる。軽量でデータ共有が容易。ただし1スレッドの暴走(不正アクセス等)が プロセス全体を巻き込む ことがある
スレッドが変数を直接共有できるのは便利ですが、複数スレッドが 同じデータを同時に読み書き すると 競合状態(race condition) が起き、結果が壊れます。ロックや原子操作といった 排他制御 が必須です。詳細は /os/concurrency-control/ を参照。
実際の設計では両者を組み合わせます。例えば多くの Web ブラウザは タブやサイトごとにプロセスを分離(クラッシュやセキュリティを隔離)しつつ、各プロセス内では 複数スレッド で描画やネットワークを並行処理します。
どう選ぶ?
- 堅牢性・隔離・セキュリティ境界 が欲しい(1つの障害を全体に波及させたくない)→ マルチプロセス
- 軽量な並行・密なデータ共有(生成/切替を安くしたい、変数を直接やり取りしたい)→ マルチスレッド
- そもそも 待ち時間(I/O)が支配的 なら、スレッドを増やすより 非同期 で1スレッドを遊ばせない設計が有効なことも → /programming/sync-async/
OS Article
プロセスとスレッドを実務で読む
TL;DRは入口です。実際に選ぶ・使う段階では、何を解決するか、何と比較するか、導入後にどこで詰まるかまで見る必要があります。
解決すること
プロセス
比較で見る軸
難易度: intermediate / カテゴリ: OS / タグ数: 4
導入後に効く点
スレッドは プロセス内の実行単位で、コード/データ/ヒープを共有。生成・切替が軽い代わりに干渉しやすい。
先に潰すリスク
用語だけ覚えても、設計・実装・運用でどこに効くかを確認しないと判断を誤る。
- 難易度
- intermediate
- カテゴリ
- OS
- タグ数
- 4
判断チェックリスト
- 自社の用途が「プロセス / スレッド」に近いか確認する。
- 強みである「プロセスは 独立した仮想メモリ空間を持つ実行単位。互いに隔離され、生成・切替コストは重い。」が本当に評価軸になるか確認する。
- 注意点の「用語だけ覚えても、設計・実装・運用でどこに効くかを確認しないと判断を誤る。」を運用で吸収できるか確認する。
- 公開値や仕様値は、対象プラン・対象機種・対象リージョンまで確認する。
- 既存システム、ID、ネットワーク、監視、バックアップとの接続方法を先に洗い出す。
- 小さく試してから、本番移行、権限設計、障害時手順、コスト監視を決める。