Dock Stay
VM とコンテナの違いを図で理解する
ガイド

VM とコンテナの違いを図で理解する

「軽量な VM」ではなく「ホストカーネルを共有する隔離プロセス」。一枚絵で違いを掴み、起動時間・イメージサイズ・隔離強度の差まで結びつける。

VM とコンテナの違いを図で理解する eyecatch

まず一枚絵で違いを掴む

コンテナの説明で最初に出てくる「VM とコンテナの違い」は、文章で読むよりスタック図を見比べるのが一番早いです。

左の VM では、各 VM が 専用のカーネル を持ち、その上にゲスト OS、ライブラリ、アプリが積まれています。

ハイパーバイザがハードウェアを仮想化し、各 VM はそれぞれ別の OS(Linux と Windows の混在も可能)を動かせます。

右のコンテナでは、各コンテナは ホスト OS のカーネルをそのまま共有 します。

コンテナの中にはアプリとそれが必要とするライブラリ・ベースイメージしか入っていません。

「専用 OS の層」がそっくり消えるため、イメージは数十 MB〜数百 MB に収まり、起動はミリ秒〜数秒で済みます。

この図 1 枚で、コンテナの長所と短所のほとんどが説明できます。

以下のセクションは、図のどこを見ているかを言葉に置き換えていくだけです。

なぜ起動が速い? — 「OS を起動しない」から

VM の起動が遅いのは、ゲスト OS のカーネルとサービスを毎回ブートしているからです。

BIOS 相当の処理から init / systemd の起動、ネットワーク設定、SSH デーモンの立ち上げ……実際の体感起動時間 30 秒〜数分の大半はここで使われます。

コンテナはホストのカーネルをそのまま使うので、OS の起動が一切ありません

やるのはほぼ次の 3 つだけ:

  1. 新しい namespace(PID / Mount / Network 等)を作る
  2. cgroups で CPU / メモリの上限を設定する
  3. コンテナの中で「最初のプロセス(PID 1)」を実行する

この 3 ステップは合計でミリ秒〜数百ミリ秒。

Web サービスの自動スケール、CI/CD のジョブ起動、docker run の使い捨て実行が現実的になっているのはこの軽さが理由です。

なぜイメージが小さい? — 「OS を含まない」から

VM のディスクイメージには ゲスト OS のすべてのファイル が含まれています。

Ubuntu Server の最小構成でも 1 GB を超え、デスクトップ環境を含めると数 GB は当たり前です。

コンテナイメージにはアプリと最小限のライブラリしか入りません。

alpine:3 は 7 MB 前後、debian:slim は 70 MB 程度。

マルチステージビルドで最終イメージを scratchdistroless にすれば、Go や Rust のバイナリ単体(数 MB)にすることもできます。

この違いは単に「ストレージが安く済む」以上の意味があります:

  • レジストリへの push / pull が速い → CI/CD のフィードバックループが短くなる
  • イメージ脆弱性スキャンの対象が減る → セキュリティリスクが減る
  • 同じノードに何百個も配置できる → クラスタの集約効率が上がる

詳しくは イメージ肥大化を防ぐマルチステージビルド で。

なぜ隔離が「やや弱い」? — 「カーネルを共有している」から

VM は CPU レベルの仮想化 で隔離されているので、ゲスト OS 内のクラッシュやカーネルバグはホストに波及しません。

これがマルチテナント SaaS のような「他社のコードを同居させる」用途で VM が選ばれる理由です。

コンテナはホストカーネルを共有するため、カーネルに致命的な脆弱性があれば全コンテナが影響を受けます

たとえば過去には CVE-2022-0185(ファイルシステム周りの脆弱性)で、コンテナからのホスト権限取得が可能になる事例もありました。

対策の典型:

  • Rootless コンテナ — root として動かさない(コンテナセキュリティ
  • gVisor / Kata Containers — ユーザー空間で別カーネルを実装したり、軽量 VM を併用したりして「コンテナの皮を被った VM」にする
  • Firecracker(micro-VM) — AWS Lambda が採用する超軽量 VM。コンテナ並みに速く、VM 並みに隔離が強い

「強い隔離 + 軽さ」を両立する方向が業界全体で進んでいるイメージです。

macOS / Windows でコンテナが動く仕組み

Linux コンテナは Linux カーネルの機能 (namespaces / cgroups / overlayfs)に依存しています。

これらは Linux カーネル固有なので、macOS や Windows ではそのままでは動きません。

手元の Mac で docker run できているのは、Docker Desktop が 裏で軽量 Linux VM を起動している からです。

同様に Windows では WSL2(これも実体は軽量 Linux VM)の上で Linux コンテナが動きます。

[ Mac ホスト OS (macOS) ]
   └─ Docker Desktop
       └─ 軽量 Linux VM (HyperKit / Apple Virtualization Framework)
           └─ Linux カーネル
               └─ コンテナ 1
               └─ コンテナ 2

「Mac でコンテナを動かす」とき、実は Mac の上に薄く Linux が乗っていて、その上にコンテナが乗っている、という二段構えになっています。

これを知っていると、「Mac で動いた Dockerfile が Linux 本番でだけ落ちる」「ファイル共有が遅い」「ARM Mac で linux/amd64 イメージを動かすと激遅」などの現象が腑に落ちます。

詳しくは arm64 vs amd64 で。

こう使い分ける — 1 行の判断軸

場面 選び方
自社マイクロサービス、社内ツール、開発環境 コンテナ
CI/CD の使い捨てジョブ コンテナ
異種 OS を同じホストに同居 (Linux + Windows 等) VM
マルチテナント SaaS で他社コードを隔離 VM または micro-VM (Firecracker)
軽さと強い隔離の両立が必要 gVisor / Kata / Firecracker
レガシーアプリでカーネルパラメータ依存 VM

信用できないコードを動かすか?」と「異種 OS が必要か?」の 2 軸でほぼ決まります。

それ以外はコンテナで困らない、というのが現代的な落としどころです。

関連トピック

関連トピック