Multiple-Source Shortest Paths

Problem Statement

Let \(\Sigma = (V, E, F)\) be a planar map with outer face \(o\), where each edge \(e\) is assigned a non-negative weight \(w(e)\).1 Call any vertex incident to \(o\) a boundary vertex of \(\Sigma\). The multiple-source shortest-path problem asks for an implicit representation of the shortest paths from \(s\) to \(t\), for all boundary vertices \(s\) and all vertices \(t\). An explicit representation of these shortest paths, for example as a shortest-path tree rooted at every node on the outer face, requires \(\Omega(n^2)\) space in the worst case. Nevertheless, the multiple-source shortest-path problem can be solved in only \(O(n\log n)\) time, in any of the following forms:

The multiple-source shortest-path problem was first posed and solved by Philip Klein in 2005. Here I’m describing a slight simplification of Klein’s algorithm published by Sergio Cabello and Erin Chambers in 2007. This algorithm plays an essential role in several efficient algorithms for planar graphs and surface graphs.

Shortest paths and slacks

The MSSP algorithm relies on a characterization of shortest paths developed by Lester For in the mid-1950s. Fix a source vertex \(s\). For each vertex \(v\), let \(\textsf{dist}(v)\) denote the shortest-path distance from \(s\) to \(v\). Let \(\textsf{pred}(v)\) denote the predecessor of vertex \(v\) (if any) in some shortest path from \(s\) to \(v\). Let \(T_s\) denote the tree of shortest paths from \(s\) to other vertices, defined so that \(\textsf{pred}(v)\) is the parent of \(v\) in \(T_s\). Finally, define the slack of each dart \(u\mathord\to v\) as \[ \textsf{slack}(u\mathord\to v) := \textsf{dist}(u) + w(u\mathord\to v) - \textsf{dist}(v) \] A dart whose slack is negative is called tense.

Ford’s generic single-source shortest path algorithm starts by assigning \(\textsf{dist}(s) = 0\) and tentatively assigning \(\textsf{dist}(v) = \infty\) for every vertex \(v\ne s\). Then as long as the graph contains at least one tense dart, the algorithm relaxes one tense dart \(u\mathord\to v\) by reassigning \(\textsf{dist}(v) \gets \textsf{dist}(u) + w(u\mathord\to v)\) and \(\textsf{pred}(v) \gets u\). When no more darts are tense, every value \(\textsf{dist}(v)\) is the correct shortest-path distance, and the predecessor pointers define a correct shortest-path tree \(T_s\).

Lemma (Ford 1953):
The following invariants hold for any shortest-path tree \(T_s\) in any edge-weighted graph \(G\):
  1. Every dart in \(G\) has non-negative slack.
  1. Every dart in a shortest path tree \(T_s\) (directed away from \(s\)) has slack zero.
  1. If shortest paths are unique, then every dart that is not in the unique shortest-path tree \(T_s\) has positive slack.

To simplify presentation, I will assume for the rest of this presentation that for every vertex \(s\) and every vertex \(t\), there is a unique shortest path from \(s\) to \(t\). In particular, for each source vertex \(s\), there is a unique shortest-path tree \(T_s\) rooted at \(s\). At the end of this note I’ll describe two easy methods to enforce this assumption.

Compact Output

Disk-tree Lemma:
Let \(T\) be any tree embedded on a disk with boundary cycle \(B\); call any vertex in \(T\cap B\) a boundary vertex. Let \(e\) be any edge of \(T\), and let \(U\) and \(W\) be the components of \(T\setminus e\). Either \(U\) contains no vertices, or \(U\) contains every boundary vertex, or boundary vertices in \(U\) induce a path in \(B\).
Let \(\Sigma\) be the planar map induced by \(T \cup B\). Trivially, \(T\) is a spanning tree of \(\Sigma\). The complementary dual spanning tree \(C^*\) of \(\Sigma^*\) is a star, with the outer face of \(\Sigma\) at the center and other faces of \(\Sigma\) at the leaves.

The dual subgraph \(C^* / e^*\) contains a cycle \(\gamma\) of length \(2\) that separates all vertices in \(U\) from all vertices in \(W\). If \(\gamma\) does not intersect \(B\), then \(U\) either contains every boundary vertex or none. Otherwise, \(\gamma\) intersects \(B\) exactly twice, so \(U\) contains an interval of boundary vertices. \(\qquad\square\)

The disk-tree lemma.

Now suppose our original planar map \(\Sigma\) has \(k\) boundary vertices, indexed \(s_0, s_1, s_2, \dots, s_{k-1}\) in cyclic order. For each index \(i\), let \(T_i\) denote the shortest-path tree rooted at \(s_i\).

Every directed edge \(x\mathord\to y\) is either in every shortest path tree \(T_i\), in no shortest path tree \(T_i\), or in an interval of shortest path trees \(T_i, T_{i+1 \bmod k}, \dots, T_{i+j \bmod k}\).
Let \(T\) be the unique tree of directed shortest paths into vertex \(y\), and apply the disk-tree lemma to the components of \(T - xy\). \(\qquad\square\).

It follows that we can encode all \(k\) shortest paths using only \(O(n)\) space, either by recording the first and last trees \(T_i\) that contain each directed edge, or by recording the initial tree \(T_1\) followed by the differences \(T_2\setminus T_1, T_3\setminus T_2\dots T_k\setminus T_{k-1}\).

Parametric Shortest Paths

To solve the multiple-source shortest path problem, imagine moving the source vertex \(s\) continuously around the outer face and maintaining the shortest-path tree \(T_s\) rooted at \(s\). Although the shortest-path distances vary continuously as \(s\) moves, the structure of the shortest-path tree changes only at discrete events. (This approach is a variant of the parametric shortest-path problem first proposed by Karp and Orlin (1981).)

Now consider a single edge \(uv\) on the outer face. Suppose we have already computed the shortest-path tree \(T_u\) rooted at \(u\), and we want to maintain the shortest path tree \(T_s\) as the source vertex \(s\) moves along \(uv\) from \(u\) to \(v\). We insert \(s\) as a new vertex, partitioning \(uv\) into two edges \(us\) and \(sv\) with parametric weights \[ w_\lambda(us) = \lambda \cdot w(uv) \qquad\text{and}\qquad w_\lambda(sv) = (1-\lambda) w(uv) \] Every other edge \(xy\) has constant parametric weight \(w_\lambda(xy) = xy\). We then maintain the shortest-path tree \(T_\lambda\) rooted at \(s\), with respect to the weight function \(w_\lambda\), as the parameter \(\lambda\) increases continuously from \(0\) to \(1\). The initial shortest-path tree \(T_0\) is equal to \(T_u\), and the final tree \(T_1\) is equal to \(T_v\).

Fix a parameter value \(\lambda \in [0,1]\). For any vertex \(x\), let \(\textsf{dist}_\lambda(x)\) denote the shortest-path distance from \(s\) to \(x\) with respect to the weight function \(w_\lambda\). Similarly, for any dart \(x\mathord\to y\), let \[ \textsf{slack}_\lambda(x\mathord\to y) = \textsf{dist}_\lambda(x) + w_\lambda(x\mathord\to y) - \textsf{dist}_\lambda(y). \] Color each vertex \(x\) red if \(\textsf{dist}_\lambda(x)\) is an increasing function of \(\lambda\) (with derivative \(1\)), and blue if \(\textsf{dist}_\lambda(x)\) is an decreasing function of \(\lambda\) (with derivative \(-1\)). For generic values of \(\lambda\), every vertex except \(s\) is either red or blue. Finally, call a dart \(x\mathord\to y\) active if \(\textsf{slack}_\lambda(x\mathord\to y)\) is a decreasing function of \(\lambda\).

The following invariants hold for all \(\lambda\in [0,1]\):
  1. If \(s\mathord\to v \not\in T_\lambda\), then every vertex except \(s\) is red, and the only active dart is \(s\mathord\to v\).
  1. If \(s\mathord\to u \not\in T_\lambda\), then every vertex except \(s\) is blue, and there are no active darts.
  1. Otherwise, every descendant of \(u\) is red, every descendant of \(v\) is blue, and \(x\mathord\to y\) is active if and only if \(x\) is blue and \(y\) is red.

Without loss of generality, assume \(o = \textsf{left}(u\mathord\to v)\) is the outer face of \(\Sigma\). Let \(p = \textsf{right}(u\mathord\to v)\) be the other face incident to \(uv\). Let \(C^*_\lambda = (E\setminus T_\lambda)^*\) denote the spanning tree of \(\Sigma^*\) complementary to \(T_\lambda\). Finally, let \(\pi_\lambda\) denote the unique directed path in \(C^*_\lambda\) from \(o^*\) to \(p^*\).

If \(T_\lambda\) has both red and blue vertices, then a dart is active if and only if its dual is in the directed path \(\pi_\lambda\).
A single pivot in a planar shortest-path tree.
If \(T_\lambda\) has both red and blue vertices, the next dart to become tense (if any) is the dart with minimum slack whose dual is in the directed path \(\pi_\lambda\).

Thus, we can execute a single phase of the MSSP algorithm as follows. Initially, we set \(s = u\). We repeatedly find the tensest active dart \(d = x\mathord\to y\), move \(s\) distance \(\textsf{slack}(d)/2\) along \(uv\), increase all red distances and decrease all blue distances by \(\textsf{slack}(d)/2\), decrease the slacks of all active darts and increase the slacks of their reversals by \(\textsf{slack}(d)\), and finally pivot \(d\) into the tree by assigning \(\textsf{pred}(y) \gets x\). The loop ends either when there are no more active darts, or when the source vertex \(s\) reaches \(v\).

Each pivot changes at least one node \(y\) from red to blue, and no pivot changes any node from blue to red. Thus, once a dart is pivoted into the shortest-path tree, it is not pivoted out during that phase. Thus, the darts that are pivoted into the tree are precisely the darts in \(T_v \setminus T_u\). The disk-tree lemma now immediately implies that the total number of pivots over all phases is only linear.

The MSSP algorithm performs a total of \(O(n)\) pivots.

Dynamic Forest Data Structures

To achieve a running time of \(O(n\log n)\), we need to perform each pivot quickly. We maintain both the shortest-path tree \(T_\lambda\) and the complementary dual spanning tree \(C^*_\lambda\) in data dynamic forest data structures that implicitly maintain dart values (slacks) or vertex values (distances) under edge insertions, edge deletions, and updates to the values in certain substructures.

We maintain the shortest path tree \(T_\lambda\) as a directed tree rooted at \(s\), with \(\textsf{dist}\) values associated with each vertex, in a data structure that supports the following operations:

Similarly, we maintain the complementary dual spanning tree \(C^*_\lambda\) as an undirected unrooted tree, with \(\textsf{slack}\) values associated with every dart, in a data structure that supports the following operations.

The self-adjusting top trees, proposed by Bob Tarjan and Renato Werneck in 2005, support all the operations we need for both data structures in in \(O(\log n)\) amortized time each. A description of self-adjusting top trees (or the splay trees they use under the hood) is unfortunately beyond the scope of this note (or this course).

The MSSP Algorithm

With these data structures in hand, we can identify the tenses active dart and perform the necessary updates to pivot it into \(T_\lambda\) in \(O(\log n)\) amortised time. The following figure shows the algorithm to perform the next pivot, with all data structure operations in place. As we already argued, the total number of pivots is \(O(n)\), so the overall algorithm runs in \(O(n\log n)\) time, as claimed.

The MSSP algorithm.

Cleaner to show only the generic case: both red and blue vertices.


Computing all \(k^2\) boundary-to-boundary distances \(O((n + k^2)\log n)\) time is straightforward.

Enforcing Unique Shortest Paths

The MSSP algorithm implicitly assumes that there is a unique shortest path between any two vertices of \(\Sigma\); in particular, for any source vertex \(s\), there is a unique shortest-path tree \(T_s\). More subtly, it also assumes that there is a unique tensest active dart. This assumption obviously does not hold in general, but we can enforce it if necessary using any of several standard perturbation techniques. I’ll describe two such techniques here, but there are other possibilities.

Standard perturbation methods either explicitly or implicitly define a secondary weight \(w’(u\mathord\to v)\) for each each dart \(u\mathord\to v\) in \(\Sigma\). The perturbed weight of a dart \(d\) is then defined as \[ \tilde{w}(d) := w(d) + w’(d)\cdot \varepsilon \] for some sufficiently small real number \(\varepsilon>0\). Rather than computing a particular value of \(\varepsilon\), we consider the limiting behavior as \(\varepsilon\) approaches zero. Thus, we can consider each perturbed weight \(\tilde{w}(d)\) to be an ordered pair or vector \[ \tilde{w}(d) := ( w(d), w’(d) ). \] We compute lengths of paths by summing these vectors normally, but we compare path lengths lexicographically. That is, we consider one path \(\pi\) to be shorter than another path \(\pi’\) if either of the following conditions holds:

  1. \(w(\pi) < w(\pi’)\)
  2. \(w(\pi) = w(\pi’)\) and \(w’(\pi) < w’(\pi’)\)

Random Perturbation

The simplest perturbation method chooses random secondary weights for each edge. For example, if we choose each secondary weight \(w’(e)\) uniformly at random from the real interval \([0,1]\), then the lengths of all simple paths (indeed, the lengths of all finite walks) are distinct with probability \(1\).

Somewhat more realistically, the following lemma implies that we can choose small random integers for the secondary weights.

Isolation Lemma (Mulmuley, Vazirani, and Vazirani 1987): Let \(\mathcal{F}\) be any family of subsets of \([n]\). For each index \(i\in [n]\), let \(w’(i)\) be chosen independently and uniformly at random from \([N]\). Define the weight \(w’(S)\) of any subset \(S\subseteq[n]\) as \(w’(S) = \sum_{i\in S} w’(i)\). With probability at least \(1-n/N\), the minimum-weight set in \(\mathcal{F}\) is unique.

Corollary: If each perturbation weight \(w’(e)\) is chosen independently and uniformly at random from \([n^4]\), then with probability \(1 - 1/O(n)\), all shortest paths with respect to the perturbed weight function \((w, w’)\) are unique.

Let me emphasize that the Isolation Lemma only implies that shortest paths are distinct; other pairs of paths may still have equal length, even after perturbation.

Cotree Perturbation

Let \(T\sqcup C\) be a tree-cotree decomposition of \(\Sigma\). Root the dual spanning tree \(C^*\) at the dual of the outer face \(o^*\), and direct all edges of \(C^*\) away from the root. We define the weight \(w’(d)\) of each dart \(d\) of \(\Sigma\) as follows:

Equivalently, for any dart \(d\not\in T\), let \(\textsf{cycle}_T(d)\) be the unique directed cycle in \(T + d\). Then \(w’(d)\) is the number of faces of \(\Sigma\) inside \(\textsf{cycle}_T(d)\) if that cycle is oriented counterclockwise, the negation of the number of interior cycles if the cycle is clockwise, and zero if \(d\) is in \(T\).

Winding Lemma:
For any closed walk \(W\) in \(\Sigma\), we have \(\sum_{d\in W} w’(d) = \sum_{f\in F} \textsf{wind}(W, f)\).
We can compute the winding number of \(W\) around \(f\) by traversing the path in \(C^*\) from \(f^*\) to \(o^*\) and counting crossings. We can write \(W\) as the sum of the fundamental directed cycles determined by the non-tree edges of \(W\). Incomplete

The previous lemma implies that although the secondary weights \(w’\) depends on the choice of tree-cotree decomposition, the resulting shortest paths do not!

For any two paths \(\pi\) and \(\pi’\) with the same endpoints, and any two spanning trees \(T\) and \(T’\), we have \(w’_T(\pi) < w’_T(\pi’)\) if and only if \(w’_{T’}(\pi) < w’_{T’}(\pi’)\). Thus, shortest paths with respect to \(w’_T\) and \(w’_{T’}\) coincide.


Cotree perturbation makes shortest paths unique.
Let \(\pi\) and \(\pi’\) be two shortest paths from some vertex \(s\) to some other vertex \(t\). By definition, we have \(w(\pi) = w(\pi’)\) and \(w’(\pi) = w’(\pi’)\). The latter condition implies that \(\sum_{f\in F} \textsf{wind}(\pi-\pi’, f) = 0\). There are two cases to consider.

First, suppose \(\pi\) and \(\pi’\) do not cross. Then the closed walk \(\pi - \pi’\) is a weakly simple closed curve, which implies that the non-zero winding numbers \(\textsf{wind}(\pi-\pi’, f)\) are either all \(1\) or all \(-1\). It follows that \(\textsf{wind}(\pi-\pi’, f) = 0\) for every face \(f\), which is only possible if \(\pi\) and \(\pi’\) use the same subset of edges. In other words, \(\pi = \pi’\).

Now suppose \(\pi\) and \(\pi’\) cross at some vertex \(x\). The prefixes \(\alpha = \pi[s, x]\) and \(\alpha’ = \pi’[s, x]\) must be shortest paths, otherwise we could shorten one of \(\pi\) and \(\pi’\). Similarly, the suffixes \(\beta = \pi[x,t]\) and \(\beta’ = \pi’[x,t]\) must be shortest paths. The inductive hypothesis now implies that \(\alpha = \alpha’\) and \(\beta = \beta’\). Again, we conclude that \(\pi = \pi’\). \(\qquad\square\)

Leftmost shortest paths

In fact, we can implement cotree perturbation without explicit secondary weights. Suppose \(\pi\) and \(\pi’\) are two paths with the same endpoints. We say that \(\pi\) is to the left of \(\pi’\) if the closed walk \(\pi-\pi’\) winds negatively around at least one face, but does not wind positive around any face. If \(\pi\) is to the left of \(\pi\)’, we immediately have \(w’(\pi) < w’(\pi’)\).

It is not hard to show that for any two paths \(\pi\) and \(\pi’\) with the same endpoints, either one path is the left of the other, or a third path is to the left of both of them. Thus, shortest paths with respect to cotree perturbation are always leftmost shortest paths.

We can simulate cotree perturbation by always breaking ties to the left. In the MSSP algorithm, we always pivot the leafmost tensest active dart.

Need more details here

Caveat Emptor!

Cotree perturbation is attractive both because it is deterministic and because it can often be implemented implicitly, but its asymmetry can be a disadvantage. Unless shortest paths are already unique, cotree perturbation yields shortest paths that are not symmetric, even when the original graph is undirected. The reversal of the leftmost shortest path from \(s\) to \(t\) is the rightmost shortest path from \(t\) to \(u\). Thus, algorithms that rely on the usual behavior of undirected shortest paths cannot automatically use this technique.

As a simple example, consider the non-crossing shortest paths problem. Given an undirected planar map \(\Sigma\) with weighted edges and several pairs of vertices \((s_1, t_1), \dots, (s_k, t_k)\) on the outer face, we want to compute shortest paths between each pair \(s_i\) and \(t_i\) that are pairwise non-crossing. If shortest paths in \(\Sigma\) are already unique, then it suffices to independently compute the shortest path in \(\Sigma\) from \(s_i\) to \(t_i\) for each index \(i\). But suppose the terminals appear in order \(s_1, t_1, s_2, t_2\) on the outer face, and we use cotree perturbation to enforce uniqueness. Then the shortest path from \(s_1\) to \(t_1\) might cross the shortest path from \(s_2\) to \(t_2\).

Leftmost shortest paths in undirected planar graphs can cross

Not appearing

  1. In fact the algorithm adapts easily to directed graphs, where a dart and its reversal may have different weights, but for ease of exposition, I’ll stick to undirected graphs in this note.↩︎