Dijkstra's Algorithm
The classic shortest-path algorithm — Branch & Bound made elegant. A* with zero intuition, and still guaranteed optimal
The Simplest Explanation
Dijkstra is Branch & Bound with better bookkeeping — or equivalently, A* with no sense of direction ( everywhere).
The idea in one sentence: always extend the cheapest path you have so far. It looks only backward at actual cost incurred (), never forward. Like water flooding outward from the source, it reaches nodes in order of their true cheapest distance.
Dijkstra = pick the unvisited node with the smallest . Once a node is visited ("colored black"), its shortest distance is final — because all edge costs are positive, no detour can ever improve it.
From Branch & Bound to Dijkstra
Branch & Bound extends the cheapest partial path each step. It works: always refining the cheapest partial solution guarantees that when a complete solution beats all remaining estimates, it's optimal. But it keeps every partial path as a separate node in a search tree — the same city appears in dozens of partial paths.
Dijkstra (1959) cleans this up:
- Keep one copy of each node in a single graph
- Store one -value and one parent pointer per node
- When a cheaper route to a node is found, just update its and re-point its parent
Same algorithmic heart, dramatically less memory.
The Algorithm
- Assign to start, to every other node; all nodes white (unvisited)
- While unvisited nodes remain:
- Pick the cheapest white node
- Color it black (visited) — its distance is now final
- For each white neighbor : relax edge :
- if , set and parent
- Stop when the goal turns black; reconstruct the path via parent pointers
When node is chosen as cheapest among all white nodes, any alternative route to must pass through some other white node with — and since edges cost , that route costs . No improvement possible. This argument requires non-negative edge costs; negative edges break Dijkstra.
Interactive Trace
Watch Dijkstra flood outward from S to goal D, updating parents whenever a cheaper route appears:
Initialize: every node gets g = ∞ except the start node, which gets g = 0. All nodes start white (unvisited).
Key Observations
- Cheapest-first ordering: after visiting S, node A () beats B () even though B was generated first.
- Parent repointing: B's parent changes from S to A when undercuts . Dijkstra handles this gracefully because each node exists once.
- No Case-3 problem: once black, a node's is never revised again — unlike A*, which may need to reopen closed nodes.
Where Dijkstra Sits in the Family
| Algorithm | Picks by | Direction | Optimal? |
|---|---|---|---|
| BFS | fewest hops | backward (hops) | Yes, unweighted only |
| Branch & Bound / UCS | cheapest partial path | backward () | Yes |
| Dijkstra | cheapest single node | backward () | Yes |
| Best-First Search | smallest | forward () | No |
| A* | smallest | both | Yes, admissible |
Dijkstra explores blindly in all directions like flood fill. On a map going south from Chennai, it will explore half of Chennai before heading toward Mahabalipuram. Adding a heuristic converts it into A* — same skeleton, plus direction.
Complexity
| Property | Value |
|---|---|
| Complete? | Yes (finite graph) |
| Optimal? | Yes, for non-negative edge costs |
| Time | with binary heap |
| Space | — one entry per node |
Compare BFS's tree explosion: Dijkstra's single-copy trick caps memory at one slot per distinct node.