Shortest paths
Weighted graphs. Which algorithm depends entirely on the weights.
Trigger in the prompt: 'Cheapest route', 'minimum cost', 'earliest time to reach'.
mediumCheapest Flights Within K Stops
Find the cheapest route with at most k intermediate stops.
Trigger'At most k stops' — a hop constraint on top of a shortest path.
Approach- Dijkstra alone is wrong: the cheapest path may exceed the stop limit.
- The constraint maps exactly onto Bellman-Ford's rounds — k+1 relaxation passes.
- Use a snapshot of the distances per round, so one round cannot cascade into itself.
- Alternative: Dijkstra with (cost, node, stops) in the state.
O(k · E) time, O(V) space.
PitfallRelaxing in place rather than from a snapshot. A single round then chains and allows more hops than allowed.
Say it out loud“The stop limit is what makes this Bellman-Ford rather than Dijkstra: k stops means k plus one rounds of relaxation, which maps onto the algorithm exactly. The detail is relaxing from a snapshot of the previous round, otherwise one pass chains through multiple edges.”
Solve on LeetCodemediumMin Cost to Connect All Points
Connect all points with minimum total edge cost.
Trigger'Connect everything at minimum cost' — a minimum spanning tree.
Approach- Name it: this is an MST.
- The graph is complete (n² implicit edges), so Prim with an adjacency-free approach beats Kruskal here — Kruskal would need to sort n² edges.
- Prim: keep the cheapest known distance from the tree to each outside point, take the minimum, add it, update.
- Kruskal is better on sparse graphs — say when you would pick each.
O(n²) with dense Prim; O(n² log n) with a heap.
PitfallReaching for Kruskal on a complete graph. Sorting n² edges is worse than dense Prim.
Say it out loud“This is a minimum spanning tree on a complete graph. Because every pair is an edge, Kruskal would have to sort n squared edges — dense Prim is n squared with no sort. On a sparse graph I'd flip that choice and use Kruskal with union-find.”
Solve on LeetCodemediumNetwork Delay Time
Find how long until a signal from one node reaches every node in a weighted directed graph.
TriggerPositive weights, single source, 'time for all to receive'.
Approach- Positive weights and one source: Dijkstra.
- Heap of (distance, node); skip stale entries with `if d > dist[u]: continue`.
- The answer is the maximum finalised distance; if any node is unreachable, return −1.
O(E log V) time, O(V + E) space.
PitfallOmitting the stale-entry check. Without it you reprocess nodes and the complexity degrades.
Say it out loud“Weights are positive and there's a single source, so Dijkstra. Python's heap has no decrease-key, so I push duplicates and skip stale entries on pop — that's the lazy deletion that gives the E log V bound.”
Solve on LeetCodemediumPath With Minimum Effort
Find the path across a grid minimising the largest single elevation change.
Trigger'Minimise the maximum edge' — a Dijkstra variant, or binary search plus BFS.
Approach- The cost of a path is a maximum, not a sum. Say that — it is the whole twist.
- Dijkstra still works: relax with max(current_effort, edge) instead of a sum.
- Alternative: binary search the threshold and check connectivity with BFS.
O(m·n·log(m·n)) with Dijkstra.
PitfallSumming the differences. The objective is a maximum, and summing gives a different answer.
Say it out loud“The twist is that path cost is a maximum rather than a sum, but Dijkstra's argument survives: the relaxation just becomes max of the running effort and the edge. There's also a binary search on the threshold with a plain BFS check, which is often easier to explain.”
Solve on LeetCodemediumShortest Path in Binary Matrix
Find the shortest clear path from corner to corner in a binary grid, moving in eight directions.
Trigger'Shortest path' on an unweighted grid.
Approach- All moves cost one, so BFS — not Dijkstra. Say that explicitly.
- Eight directions, so the neighbour list has eight offsets.
- Then the extension: A* with the Chebyshev heuristic, because diagonal movement is allowed.
- Say why Manhattan would be wrong here: it overestimates with diagonals, so it is not admissible and you lose optimality.
O(n²) time and space with BFS.
PitfallUsing the Manhattan heuristic with eight-directional movement. It overestimates and breaks the optimality guarantee.
Say it out loud“Every move costs the same, so BFS is enough — Dijkstra would be overkill. If we want to expand fewer nodes, A* with a Chebyshev heuristic works, since diagonals are allowed. Manhattan would overestimate here, which makes it inadmissible and loses the optimality guarantee.”
Solve on LeetCodehardSliding Puzzle
Find the fewest moves to solve a small sliding tile puzzle.
Trigger'Fewest moves' over a state space rather than a map.
Approach- The graph is the state space: each board configuration is a vertex, each legal move an edge.
- Encode the board as a string or tuple so it can be hashed into the visited set.
- BFS gives the optimal move count since every move costs one.
- A* with the sum of Manhattan distances is the natural improvement — and it is admissible because each move fixes at most one tile's distance by one.
O(states) with BFS; far fewer expansions with A*.
PitfallNot hashing the state. Without a visited set the search revisits configurations endlessly.
Say it out loud“The graph here is implicit — vertices are board states. I encode each board as a tuple so it can go in a visited set, and BFS gives the optimal move count. A* with summed Manhattan distances is admissible, because one move can only reduce one tile's distance by one, and it cuts the expansions dramatically.”
Solve on LeetCodehardSwim in Rising Water
Find the earliest time you can cross a grid where each cell becomes passable at its own height.
Trigger'Earliest time', with cells unlocking over time — the same minimax-path shape.
Approach- Same structure as minimum effort: the cost of a path is the maximum cell value on it.
- Dijkstra with max-relaxation, or binary search on the time plus a BFS reachability check.
- Union-find sorted by height also works: add cells in height order until start and end connect.
O(n² log n) with Dijkstra on an n×n grid.
PitfallTreating it as a sum of heights. It is a bottleneck path, not a shortest path.
Say it out loud“This is the same minimax-path problem as minimum effort: I want the path whose highest cell is lowest. Dijkstra with a max relaxation gives it directly. The union-find version is elegant — add cells in increasing height until the two corners connect.”
Solve on LeetCode