Containers vs Virtual Machines
Two Ways to Isolate Software
Before containers, the standard way to give an app "its own machine" was a virtual machine (VM): software that pretends to be an entire physical computer - a virtual CPU, virtual disk, virtual network card - and boots a full guest operating system (with its own kernel, the core program that talks directly to hardware) on top of that pretend hardware. It works, but it's heavy: booting a whole OS takes real time and real memory, every single time you start one.
A container takes a completely different shortcut. It doesn't pretend to be a computer at all - it's just an ordinary program (a process, the same kind of thing as a running text editor or web browser) on the host machine, given the illusion that it's alone on its own system. Two Linux kernel features create that illusion:
- Namespaces - control what the process can see. A namespaced process gets its own private view of the filesystem, its own list of "running processes" (it can't see the host's), its own network interfaces, its own hostname - even though, underneath, it's running right alongside everything else on the same machine.
- cgroups (control groups) - control what the process can use. They cap how much CPU, memory, and number of processes (PIDs) a container is allowed to consume, so one greedy container can't starve the rest of the machine.
Analogy: Namespaces are like giving someone a private office with frosted-glass walls - they can only see their own desk, not the rest of the building, even though they're in the very same building as everyone else. cgroups are like a metering valve on that office's water and electricity - they can use what they're allotted, no more.
VM: App → Guest OS (full kernel) → Hypervisor → Host OS → Hardware
Container: App → Container runtime → Host OS (shared kernel) → Hardware
| Virtual Machine | Container | |
|---|---|---|
| Boots in | minutes | milliseconds |
| Size | gigabytes | megabytes |
| Kernel | its own | shared with host |
| Isolation | very strong (hardware-level) | good (kernel-level) |
| Density per host | tens | hundreds |
Note: Containers share the host kernel. That's why they start instantly and stay tiny - and also why container security matters: a kernel exploit inside a container threatens the host. (More in the Security module.)
Tip: It's not either/or in real infrastructure - cloud providers typically run your containers inside VMs, combining VM isolation between customers with container speed for deployment.