Skip to main content

Shortest Path Algorithms

Shortest Path Algorithm Selection

Algorithm Selection Guide

Pattern Recognition Signals:
  • “Shortest path” with all weights = 1 → BFS
  • “Minimum cost path” with non-negative weights → Dijkstra
  • “Negative weights” or “detect negative cycle” → Bellman-Ford
  • “All pairs shortest path” with small n (≤400) → Floyd-Warshall
  • Weights are only 0 and 1 → 0-1 BFS

Dijkstra’s Algorithm

Dijkstra's Algorithm Visualization The workhorse for single-source shortest path with non-negative weights. Analogy: Imagine a fire starting at the source node and spreading through the graph. The fire reaches closer nodes first, then spreads to farther ones. The priority queue ensures we always process the closest unvisited node, just like fire always advances through the shortest fuel path first. Why it works: Dijkstra greedily finalizes the closest unvisited node. With non-negative weights, once a node is finalized, no future path through unvisited nodes could be shorter (they would have to pass through nodes that are farther away and add non-negative weight). This greedy property breaks with negative weights.

Standard Implementation

Path Reconstruction

Critical Mistake: Using int for distances With weights up to 10^9 and paths up to 10^5 edges, total distance can exceed 10^14. Use long long.

0-1 BFS

For graphs where edges have weight 0 or 1. Uses deque instead of priority queue. Why it works: With only 0 and 1 weights:
  • 0-weight edges don’t increase distance → add to front of deque
  • 1-weight edges increase distance by 1 → add to back of deque
This maintains the invariant that the deque is sorted by distance (like a priority queue, but O(1) instead of O(log n) per operation). When to Use:
  • Grid problems where moving is free but breaking walls costs 1
  • Graphs with binary edge weights
  • Faster than Dijkstra: O(V + E) vs O(E log V)
Classic Application: Grid with blocked cells that cost 1 to break through.

Bellman-Ford Algorithm

Handles negative edge weights and detects negative cycles. Why Dijkstra Fails with Negative Weights: Dijkstra assumes once a node is “finalized,” its distance can’t improve. With negative edges, this breaks—a longer path might become shorter later! The Insight: After at most (n-1) relaxations of all edges, shortest paths are found (if no negative cycle). Why n-1? The longest simple path has n-1 edges. Negative Cycle Detection: If any distance improves on the nth iteration, there’s a negative cycle—distances can decrease infinitely! When to Use:
  • Negative edge weights (Dijkstra fails)
  • Need to detect negative cycles
  • Sparse graphs with few edges

Finding Negative Cycle


Floyd-Warshall Algorithm

Computes all-pairs shortest paths. Works with negative weights (but no negative cycles). The Idea: For each pair (i, j), try using each vertex k as an intermediate point. dist[i][j]=min(dist[i][j],dist[i][k]+dist[k][j])dist[i][j] = \min(dist[i][j], dist[i][k] + dist[k][j]) Why the loop order matters: We iterate k on the outside. After iteration k, dist[i][j] contains the shortest path using only vertices 1 to k as intermediates. Complexity: O(V³)—only use when V ≤ 400 When to Use:
  • Need all pairs shortest paths
  • Graph is dense (many edges)
  • V is small (≤ 400)

Detecting Negative Cycles with Floyd-Warshall

After running the algorithm, check if any dist[i][i] < 0.

SPFA (Bellman-Ford Optimization)

Shortest Path Faster Algorithm—optimized Bellman-Ford with queue.
SPFA has worst-case O(VE) and can be slow on adversarial inputs. Many competitive programming judges include anti-SPFA test cases specifically to fail this algorithm. Prefer Dijkstra for non-negative weights. Only use SPFA when you need Bellman-Ford’s capabilities (negative weights) with potentially faster average performance.

Pattern 1: Multi-Source Shortest Path

Problem: Find shortest path from any of K source nodes. Solution: Add all sources to initial queue/priority queue.

Pattern 2: Shortest Path with Constraints

Problem: Shortest path with at most K edges, or at most K toll roads. Solution: Add state dimension.

Pattern 3: Shortest Path on DAG

Problem: Shortest path in a Directed Acyclic Graph. Solution: Topological sort + DP. O(V + E).

Pattern 4: Meet in the Middle (Bidirectional)

Problem: Shortest path from A to B in a very large graph. Solution: Run Dijkstra from both ends.

Common Mistakes

Mistake 1: Wrong INF value Use 1e18 for long long. Using INT_MAX causes overflow when adding: INT_MAX + 1 wraps to a negative number, which then appears “shorter” than real distances.
Mistake 2: Not handling disconnected components If destination is unreachable, return -1, not INF. Many problems penalize printing a huge number instead of -1 or “impossible.”
Mistake 3: Using Dijkstra with negative weights Dijkstra does NOT work with negative edges. Use Bellman-Ford or SPFA. Even a single negative edge can make Dijkstra produce wrong answers, because it finalizes nodes greedily under the assumption that distances only increase.
Mistake 4: Multiple edges between the same pair of nodes When reading the graph, always take the minimum weight if there are parallel edges:

Practice Problems

Beginner (1000-1300)

Intermediate (1300-1600)

Advanced (1600-1900)


Key Takeaways

Dijkstra for Non-Negative

O(E log V), most common algorithm in CP.

Bellman-Ford for Negative

O(VE), detects negative cycles.

Floyd for All-Pairs

O(V³), when you need all pairs and n ≤ 400.

0-1 BFS for Binary

O(V + E), when weights are only 0 and 1.

Next Up

Chapter 15: Trees

Master tree traversals, LCA, and tree DP for hierarchical structures.