Nearly Maximum Flows in Nearly Linear Time

Jonah Sherman

Introduction

In this paper, we introduce a new approach to this problem in undirected graphs. We maintain a flow that may not quite route bb exactly, but we also keep track of an upper bound on how much it will cost us in congestion to fix it back up. We will aim to minimize a potential function measuring the current congestion plus an over-estimate on the cost of fixing up the residuals. By not needing to worry about precisely conserving flow at every vertex, we can take large steps in each iteration towards minimizing our potential function. On the other hand, by intentionally over-estimating the cost of fixing up the residuals, in the course of minimizing our potential function we must inevitably fix them up, as it will cost strictly less to do so.

For a graph GG, let CC be the m×mm\times m diagonal matrix containing the edge capacities, and let BB be the n×mn\times m divergence matrix, where (Bf)i(Bf)_{i} is the excess at vertex ii. For a set S⊆VS\subseteq V, we’ll write bS=∑i∈SbSb_{S}=\sum_{i\in S}b_{S}, the total excess in SS, and cS=∑e:S↔V∖Scec_{S}=\sum_{e:S\leftrightarrow V\setminus S}c_{e}, the capacity of the cut (S,V∖S)(S,V\setminus S) in GG. A valid demand vector satisfies bV=0b_{V}=0.

The minimum congestion flow problem for demands bb, and its dual, the maximum congested cut, are

We refer to the optimum value of these problems as opt(b)\mathsf{opt}(b). It is well-known that for problem (2), one of the threshold cuts with respect to vv achieves bS/cS≥b⊤vb_{S}/c_{S}\geq b^{\top}v.

2 Outline

An α\alpha-congestion-approximator for GG is a matrix RR such that for any demand vector bb,

Our main result is that we can use good congestion approximators to quickly find near-optimal flows in a graph. We prove the following theorem in section 2.

For the sake of giving the reader a concrete example of what a congestion-approximator might look like before continuing, we’ll begin with two simple toy examples.

Let TT be a maximum weight spanning tree in GG, and let RR be the n−1×nn-1\times n matrix with a row for each edge in TT, and

where (S,V∖S)(S,V\setminus S) is the cut in GG induced by removing ee from TT.

Then, RR is a mm-congestion-approximator.

Since (Rb)e(Rb)_{e} is the congestion on the cut in GG induced by removing ee from TT, certainly opt(b)≥∥Rb∥∞\mathsf{opt}(b)\geq\|Rb\|_{\infty}. On the other hand, at least 1/m1/m of the capacity of those cuts is contained in TT, so routing bb through TT congests ee by at most m∣(Rb)e∣m|(Rb)_{e}|. Multiplication by RR and R⊤R^{\top} can be done in O(n)O(n) time via elimination on leaves. ∎

For graphs of large conductance, we can obtain a trivial approximator by simply looking at how much the demand into each vertex congests its total degree.

Let GG have conductance ϕ\phi. Let RR be n×nn\times n diagonal matrix with Ri,i=1/deg⁡(i)R_{i,i}=1/\deg(i) where deg⁡(i)=c{i}\deg(i)=c_{\{i\}}. Then, RR is a ϕ−1\phi^{-1}-congestion-approximator.

Routing ∣bi∣|b_{i}| into or out of vertex ii certainly must congest one of its edges by at least ∣bi∣/deg⁡(i)|b_{i}|/\deg(i), so opt(b)≥∥Rb∥∞\mathsf{opt}(b)\geq\|Rb\|_{\infty}. On the other hand, the capacity of any cut in GG is at least ϕ\phi times the total degree of the smaller side. It follows that if no vertex is congested by more than β\beta, then no cut is congested by more than ϕ−1β\phi^{-1}\beta. ∎

Congestion Potential

The key to our scheme lies transforming problem (1) to an unconstrained optimization problem, using the congestion-approximator to bound the cost of routing the residual. To that end, we introduce our potential function.

Each iteration requires O(m)O(m) time plus a multiplication by RR and R⊤R^{\top}.

The flow ff may not quite route the demands we wanted. Fortunately, that will be easy to fix. The extra factor of two in equation (3) means that half of the contribution to the objective value from the residual part is pure slack. On the other hand, if ff is nearly optimal, there can’t be too much slack.

Suppose ∥C−1f∥∞+2α∥R(b−Bf)∥∞≤(1+ε)opt(b)\|C^{-1}f\|_{\infty}+2\alpha\|R(b-Bf)\|_{\infty}\leq(1+\varepsilon)\mathsf{opt}(b). Then, ∥R(b−Bf)∥∞≤ε∥Rb∥∞\|R(b-Bf)\|_{\infty}\leq\varepsilon\|Rb\|_{\infty}.

Let ff meet the assumption. Let f′f^{\prime} be a routing of b−Bfb-Bf in GG with ∥C−1f′∥∞≤α∥R(b−Bf)∥∞\|C^{-1}f^{\prime}\|_{\infty}\leq\alpha\|R(b-Bf)\|_{\infty}. Then, moving from ff to f+f′f+f^{\prime} decreases the objective value by atleast α∥R(b−Bf)∥\alpha\|R(b-Bf)\|. On the other hand, that decrease can’t exceed εopt(b)\varepsilon\mathsf{opt}(b). Since opt(b)≤α∥Rb∥∞\mathsf{opt}(b)\leq\alpha\|Rb\|_{\infty}, the lemma follows. ∎

So while AlmostRoute may not route bb, our bound for the congestion to route the residual is at most half of our bound to route the original demands. Furthermore, the objective already pays the cost of routing that residual. In fact, it pays it with a factor of two, so we need only route the remaining residual within a factor-two of optimal. That suggests an obvious way to route demands bb: repeatedly invoke AlmostRoute on the remaining residual, until the congestion required to route it is extremely small compared to the congestion required to route bb. Then route the final residual in a naive way, such as via a maximal spanning tree. The cost of that final routing will be paid for by the slack in the objective value of the first routing, simply by finding a factor 3/23/2-optimal routing for each residual after the first case.

Formalizing the latter argument completes our proof of theorem 1.2. Set b0←bb_{0}\leftarrow b, and let (f0,S0)←AlmostRoute(b0,ε)(f_{0},S_{0})\leftarrow\mathtt{AlmostRoute}(b_{0},\varepsilon). Next for i=1,…,Ti=1,\ldots,T where T=log⁡(2m)T=\log(2m), set bi←bi−1−Bfi−1b_{i}\leftarrow b_{i-1}-Bf_{i-1} and (fi,Si)←AlmostRoute(bi,1/2)(f_{i},S_{i})\leftarrow\mathtt{AlmostRoute}(b_{i},1/2) (we don’t actually need any SiS_{i} after S0)S_{0}). Finally, let bT+1=bt−Bftb_{T+1}=b_{t}-Bf_{t}, and let fT+1f_{T+1} be a flow routing bT+1b_{T+1} in a maximal spanning tree of GG. Output f1+⋯+fT+1f_{1}+\cdots+f_{T+1} and S0S_{0}. Observe that theorem 2.1 yields

Beginning with the former inequality and repeatedly applying the latter yields,

On the other hand, by choice of TT, we have

We approximate ∥⋅∥∞\|\cdot\|_{\infty} using the symmetric softmax function.

We make use of some elementary facts about lmax⁡\operatorname{lmax}.

We will approximate problem (3) with the potential function,

Since equation (7) approximates equation (3) to within an additive θ(log⁡n)\theta(\log n), we will be concerned with minimizing ϕ(f)\phi(f) after scaling f,bf,b so ϕ(f)=θ(ε−1log⁡n)\phi(f)=\theta(\varepsilon^{-1}\log n).

AlmostRoute(b,ε)\mathtt{AlmostRoute}(b,\varepsilon): • Initialize f=0f=0, scale bb so 2α∥Rb∥∞=16ε−1log⁡(n)2\alpha\|Rb\|_{\infty}=16\varepsilon^{-1}\log(n). • Repeat: – While ϕ(f)<16ε−1log⁡(n)\phi(f)<16\varepsilon^{-1}\log(n), scale ff and bb up by 17/1617/16. – Set δ←∥C∇ϕ(f)∥1\delta\leftarrow\|C\nabla\phi(f)\|_{1}. – If δ≥ε/4\delta\geq\varepsilon/4, set fe←fe−δ1+4α2sgn⁡(∇ϕ(f)e)cef_{e}\leftarrow f_{e}-\frac{\delta}{1+4\alpha^{2}}\operatorname{sgn}(\nabla\phi(f)_{e})c_{e} – Otherwise, terminate and output ff together with the potentials induced by ∇ϕ(f)\nabla\phi(f)(see below), after undoing any scaling.

Each step requires computing ∇ϕ(f)\nabla\phi(f), which requires O(m)O(m) time plus a multiplication by RR and a multiplication by R⊤R^{\top}. Further, the partial derivative of the residual part for a particular edge is equal to a potential difference between the endpoints of that edge. When ϕ(f)\phi(f) is nearly-optimal, those potentials yield a good dual solution for our original problem.

When AlmostRoute\mathtt{AlmostRoute} terminates, we have a flow ff and potentials vv with,

Set x1=C−1fx_{1}=C^{-1}f, x2=2αR(b−Bf)x_{2}=2\alpha R(b-Bf), and pi=∇lmax⁡(xi)p_{i}=\nabla\operatorname{lmax}(x_{i}). Set v=R⊤p2v=R^{\top}p_{2} to be our potentials. Observe that ∇ϕ(f)=C−1p1−2αB⊤v\nabla\phi(f)=C^{-1}p_{1}-2\alpha B^{\top}v. First, equation (4) yields

By equation (5), using the fact that CC and RR have at most n2/2n^{2}/2 rows and ϕ(f)≥16ε−1log⁡n\phi(f)\geq 16\varepsilon^{-1}\log n,

Altogether, using the fact that δ<ε/4\delta<\varepsilon/4 at termination, we have

Observing that ϕ(f)\phi(f) overestimates ∥C−1f∥∞+2α∥R(b−Bf)∥∞\|C^{-1}f\|_{\infty}+2\alpha\|R(b-Bf)\|_{\infty} completes the proof. ∎

Let us call the iterations between each scaling a phase. Since ∥Rb∥∞\|Rb\|_{\infty} gives us the correct scale to within factor α\alpha, we will scale at most O(log⁡α)O(\log\alpha) times.

Let he=−δ1+4α2sgn⁡(∇fϕ(f)e)ceh_{e}=-\frac{\delta}{1+4\alpha^{2}}\operatorname{sgn}(\nabla_{f}\phi(f)_{e})c_{e} be our step. Then, equation (6), together with the fact that ∥RBC∥∞→∞≤1\|RBC\|_{\infty\to\infty}\leq 1 for a congestion-approximator RR yields,

Since we raised ϕ(f)\phi(f) by at most ε−1log⁡n\varepsilon^{-1}\log n when scaling, and each step drops ϕ(f)\phi(f) by at least Ω(ε2α−2)\Omega(\varepsilon^{2}\alpha^{-2}), there can be at most O(α2ε−3log⁡n)O(\alpha^{2}\varepsilon^{-3}\log n) steps between phases. ∎

Computing Congestion-Approximators

In this section we prove theorem 1.5, using a construction of Madry, itself based on a construction of Spielman and Teng.

A jj-tree is a graph formed by the union of a forest with jj components, together with a graph HH on jj vertices, one from each component. The graph HH is called the core.

Each GiG_{i} is a O(mlog⁡m/t)O(m\log m/t)-tree, with a core containing at most mm edges.

We briefly remark that while the statement of theorem 3.2 in contains an additional logarithmic dependence on the capacity-ratio of GG, that dependence is easily eliminated. We elaborate further in appendix A. Our construction will simply apply theorem 3.2 recursively, sparsifying the core on each iteration. To accomplish that, we use an algorithm of Benczúr and Karger.

Further, the edges of G′G^{\prime} are scaled versions of a subset of edges in GG, with no edge scaled by more than (1+ε)m/m′(1+\varepsilon)m/m^{\prime}.

We now present the algorithm for computing the data structure representing a congestion-approximator. The algorithm ComputeTrees\mathtt{ComputeTrees} assumes its input is sparse; our top-level data-structure is constructed by invoking ComputeTrees(Sparsify(G,1),n1/k)\mathtt{ComputeTrees}(\mathtt{Sparsify}(G,1),n^{1/k}), where kk is the parameter of theorem 1.5.

ComputeTrees(G,t)\mathtt{ComputeTrees}(G,t): • If n=1n=1, return. • Using theorem 3.2, compute distribution (λi,Gi)it′(\lambda_{i},G_{i})_{i}^{t^{\prime}} of max⁡(1,n/t)\max(1,n/t)-trees. • Pick the tt graphs of largest λi\lambda_{i}, throw away the rest, and scale the kept λi\lambda_{i} to sum to 11. • For i=1,…,ti=1,\ldots,t: – Hi′←Sparsify(Hi,1)H_{i}^{\prime}\leftarrow\mathtt{Sparsify}(H_{i},1), where HiH_{i} is the core of GiG_{i} – Li←ComputeTrees(Hi′,t)L_{i}\leftarrow\mathtt{ComputeTrees}(H_{i}^{\prime},t) • Return the list L=(λi,Fi,Li)i=1tL=(\lambda_{i},F_{i},L_{i})_{i=1}^{t} where FiF_{i} is the forest of GiG_{i}.

The analysis of ComputeTrees\mathtt{ComputeTrees} correctness will make use of another algorithm for sampling trees. The SampleTree\mathtt{SampleTree} procedure is only used for analysis, and is not part of our flow algorithm.

SampleTree(L=(λi,Fi,Ti)it)\mathtt{SampleTree}(L=(\lambda_{i},F_{i},T_{i})_{i}^{t}): • Pick ii with probability λi\lambda_{i}. • Output Fi+SampleTree(Ti)F_{i}+\mathtt{SampleTree}(T_{i})

By induction on nn. For n=1n=1 the claim is vacuous, so suppose n=tk+1n=t^{k+1}. Since GG has O(nlog⁡n)O(n\log n) edges, the distribution output by theorem 3.2 will have O(tlog⁡2n)O(t\log^{2}n) entries. We have Hi′≥HiH_{i}^{\prime}\geq H_{i} and Hi+Fi≥GH_{i}+F_{i}\geq G. Furthermore, the inductive hypothesis implies that every tree TiT_{i} in SampleTree(Li)\mathtt{SampleTree}(L_{i}) dominates Hi′H_{i}^{\prime}. Then,

Sparsifying the distribution from O(tlog⁡2n)O(t\log^{2}n) to tt scales λi\lambda_{i} by at most O(log⁡2n)O(\log^{2}n), so that ∑i=1tλiGi\sum_{i=1}^{t}\lambda_{i}G_{i} is routable in GG with congestion at most log⁡2n\log^{2}n larger than the original distribution. Since Hi′≤2HiH_{i}^{\prime}\leq 2H_{i}, by the multicommodity max-flow/min-cut theorem Hi′H_{i}^{\prime} is routable in HiH_{i} with congestion O(log⁡n)O(\log n). By the inductive hypothesis, E[SampleTree(Li)]\mathbf{E}[\mathtt{SampleTree}(L_{i})] is routable in Hi′H_{i}^{\prime} with congestion log⁡O(k)(n)\log^{O(k)}(n). It follows then that E[SampleTree(L)]\mathbf{E}[\mathtt{SampleTree}(L)] is routable in GG with congestion at most log⁡O(k+1)(n)\log^{O(k+1)}(n).

Since the capacity of each tree-edge dominates the capacity of the corresponding cut in GG, opt(b)≥∥Rb∥∞\mathsf{opt}(b)\geq\|Rb\|_{\infty}. On the other hand, bb can be routed in every tree with congestion ∥Rb∥∞\|Rb\|_{\infty}. By routing a Pr[T]\mathbf{Pr}[T] fraction of the flow through tree TT, we route bb in E[SampleTree(L)]\mathbf{E}[\mathtt{SampleTree}(L)] with congestion ∥Rb∥∞\|Rb\|_{\infty}. But then bb can be routed in GG while congesting by at most an α\alpha factor larger.

The total number of edges in RR satisfies the recurrence E(n)≤nt+tE(n/t)E(n)\leq nt+tE(n/t) as each edge is either in one of the tt toplevel forests, or in one of the tt subgraphs. ∎

Having constructed our representation of RR, it remains only to show how to multiply by RR and R⊤R^{\top}. We use the following lemmas as subroutines, which are simple applications of leaf-elimination on trees.

There is an algorithm TreeFlow\mathtt{TreeFlow} that, given a tree TT and a demand vector bb, takes O(n)O(n) time and outputs for each tree edge, the flow along that edge when routing bb in TT.

There is an algorithm TreePotential\mathtt{TreePotential} that, given a tree TT annotated with a price pep_{e} for each edge, takes O(n)O(n) time and outputs a vector of vertex potentials vv such that, for any i,ji,j, the sum of the prices on the path from jj to ii in TT is vi−vjv_{i}-v_{j}.

We begin with computing RR. We take as input the demand vector bb, and then annotate each forest edge ee with the congestion rer_{e} induced by routing bb through a tree containing ee.

ComputeR(b,L=(λi,Fi,Ti)it)\mathtt{Compute}R(b,L=(\lambda_{i},F_{i},T_{i})_{i}^{t}): • For i=1,…,ti=1,\ldots,t: – Let TT be the tree formed by taking FiF_{i}, adding a new vertex ss, and an edge from ss to each core-vertex of FiF_{i}. Augment bb with demand zero to the new vertex. – f←TreeFlow(b,T)f\leftarrow\mathtt{TreeFlow}(b,T). – Set re←fe/cer_{e}\leftarrow f_{e}/c_{e} for each forest edge in FiF_{i}. – Set b′b^{\prime} to a vector indexed by core-vertices, with bj′b^{\prime}_{j} equal to the flow on the edge from ss to core-vertex jj. – ComputeR(b′,Ti)\mathtt{ComputeR}(b^{\prime},T_{i}).

Let L=(λi,Fi,Ti)itL=(\lambda_{i},F_{i},T_{i})_{i}^{t}. We argue by induction on the depth of recursion. Fix a level and index ii. Observe that the cut in GG induced by cutting a forest edge is the same regardless of what tree TT lies on the core: it is the cut that separates the part of FiF_{i} not containing the core from the rest of the vertices. It follows that we may place any tree on the core vertices, invoke TreeFlow\mathtt{TreeFlow}, and obtain the flow on each forest edge. Next, for each component SS of FiF_{i}, the total excess bSb_{S} must enter SS via the core vertex. It follows that in a flow routing bb on Fi+T′F_{i}+T^{\prime}, for any tree T′T^{\prime}, the restriction of that flow to T′T^{\prime} must have excess bSb_{S} on the core vertex of SS, so it suffices to find a flow in the core with demands bj′=bSjb^{\prime}_{j}=b_{S_{j}}. But routing bb in Fi+TF_{i}+T will place exactly bSjb_{S_{j}} units of flow on the edge from ss to core-vertex jj.

To compute R⊤R^{\top}, we assume each forest edge ee has been annotated with a price pep_{e} that must be paid by any flow per unit of congestion on that edge, and output potentials vv such that vi−vjv_{i}-v_{j} is the total price to be paid for routing a unit of flow from jj to ii.

ComputeR⊤(L=(λi,Fi,Ti)it)\mathtt{Compute}R^{\top}(L=(\lambda_{i},F_{i},T_{i})_{i}^{t}): • v←0v\leftarrow 0 • For i=1,…,ti=1,\ldots,t: – v′←ComputeR⊤(Ti)v^{\prime}\leftarrow\mathtt{Compute}R^{\top}(T_{i}). – Let TT be the tree formed by taking FiF_{i}, adding a vertex ss, and an edge from ss to each core-vertex of FiF_{i}. Set qe=pe/ceq_{e}=p_{e}/c_{e} for each forest edge, and qe=vj′q_{e}=v^{\prime}_{j} for edge ee from ss to core-vertex jj. – v′′←TreePotential(T,q)v^{\prime\prime}\leftarrow\mathtt{TreePotential}(T,q) – Add v′′v^{\prime\prime} to vv after removing the entry for ss. • Return vv

Given edges annotated with per-congestion prices, the procedure ComputeR⊤(L)\mathtt{Compute}R^{\top}(L) correctly returns potentials vv such that vk−vjv_{k}-v_{j} is the cost per unit of flow from vertex jj to kk.

Let L=(λi,Fi,Ti)itL=(\lambda_{i},F_{i},T_{i})_{i}^{t}. We argue by induction on the depth of recursion. Fix a level; a flow must pay its toll to each GiG_{i}, so the resulting potential equals the sum of the potentials for each ii. Fix an index ii. A unit of flow from jj to kk is first routed from jj to the core-vertex of the component of FiF_{i} containing jj, then to the core-vertex of the component containing kk, and then finally to kk. By induction, we assume that v′v^{\prime} yields potentials that give the per-unit costs of routing between core-vertices. Placing a star on the core with the edge from ss to core-vertex jj having per-unit cost vj′v^{\prime}_{j} preserves those costs. If pep_{e} is the price of an edge per unit of congestion, then qe=pe/ceq_{e}=p_{e}/c_{e} is the price of an edge per unit of flow. It follows that the total toll paid is the same as the toll paid in TT; thus, the potentials output by TreePotential(T,q)\mathtt{TreePotential}(T,q) are correct.

Final Remarks

We remark that there are many other ways to obtain good congestion approximators. The oblivious routing schemes of require polynomial time to compute, but, once computed, give us a single tree whose single-edge cuts yield a log⁡(n)O(1)\log(n)^{O(1)}-congestion approximator. Furthermore, we only need the actual tree, and not the routings of the tree back in the original graph. If such a single tree could be computed in nearly-linear time, it would make an ideal candidate for use in our algorithm.

There have been substantial simplifications to Spielman and Teng’s original algorithm (see ). It may be possible to use some of those techniques to further simplify our algorithm.

References

Appendix A Fixing Theorem 3.2

The proof of theorem 3.2 maintains a length function l(e)l(e) for each edge, and repeatedly invokes an algorithm SmallStretchTree\mathtt{SmallStretchTree} that returns a spanning tree TT on GG with,

where lT(e)l_{T}(e) is the length of the path between ee’s endpoints in the tree. Without loss of generality, by scaling, we assume ∑el(e)c(e)=m\sum_{e}l(e)c(e)=m. Let χ(e,e′)=1\chi(e,e^{\prime})=1 if e′e^{\prime} is a tree edge that lies on the path in TT containing ee. Then,

where cT(e′)c_{T}(e^{\prime}) is the total capacity of edges routed through e′e^{\prime} in TT.