How to recognise
the shortest path when every step costs the same, the minimum number of moves, or a tree read level by level.
How to solve problems like this
- If the root can be none, return the empty answer first.
- Put the root in the queue.
- Each round, read size = queue.size and take exactly that many nodes: they are one level.
- Put each node's left and right child at the back, skipping none. For the rightmost value, an average or a zigzag, change only what you do with each level.
Variant: Graph
The same, but in a graph several paths lead to one vertex, so visited vertices are marked. The first time the wave reaches a vertex is the shortest path to it.
- Decide what a node is (a cell, a word, a state) and what its neighbours are.
- Put the start in the queue and mark it visited right away.
- Take from the front. Put each unvisited neighbour at the back and mark it visited as you add it.
- For distances, go level by level or store the distance with each node. Stop when you reach the target.
Variant: Grid
The same, but on a grid: cells are vertices and neighbouring cells are connected. The wave spreads from the start, and the step at which it reaches a cell is the shortest distance to it.
- Treat each open cell as a node: its neighbours are the cells above, below, left and right that are inside the grid and not walls.
- Keep a dist table filled with none. Set the start to 0 and put it in the queue.
- Take a cell from the front. Give each neighbour with no distance yet one more than this cell, and put it at the back.
- Stop when the target leaves the queue: its distance is final. A cell that is never reached keeps none.
- With several sources, like every rotten orange at once, put them all in the queue at distance 0 before the loop starts.
Variant: States
The same, but the vertices are states, such as words that differ by one letter, not places. The graph is not built in advance: a state's neighbours are made up when it is reached.
- Decide what one state is: a word, the dials of a lock, a square on a board. One move is one edge.
- Write a function that makes the neighbours of a state; do not build the whole graph up front.
- Run BFS from the start and store the moves in dist. A state already in dist is skipped, so nothing is queued twice.
- A board game works the same: in Snakes and Ladders each square is a node, a die roll gives up to six neighbours, and a snake or ladder moves you on before the square is queued.
Where it's used
- Downloading a site. wget --recursive downloads a site in waves: the start page first, then the pages it links to, then the next layer. The -l option limits how many waves to go.
- Garbage collection. A copying collector built on Cheney's algorithm moves live objects to a new area in waves: first the ones the program points to, then the ones they point to. The new area itself serves as the queue.