5 Runs the highest label variant of the preflow push algorithm with
6 running time O(n^2\sqrt(m)), with the 'empty level' and with the
7 heuristic that the bound b on the active nodes is not increased
8 only when b=0, when we put b=2*n-2.
10 'A' is a parameter for the empty_level heuristic
14 void run() : runs the algorithm
16 The following functions should be used after run() was already run.
18 T maxflow() : returns the value of a maximum flow
20 T flowonedge(EdgeIt e) : for a fixed maximum flow x it returns x(e)
22 FlowMap allflow() : returns the fixed maximum flow x
24 void mincut(CutMap& M) : sets M to the characteristic vector of a
25 minimum cut. M should be a map of bools initialized to false.
27 void min_mincut(CutMap& M) : sets M to the characteristic vector of the
28 minimum min cut. M should be a map of bools initialized to false.
30 void max_mincut(CutMap& M) : sets M to the characteristic vector of the
31 maximum min cut. M should be a map of bools initialized to false.
46 template <typename Graph, typename T,
47 typename FlowMap=typename Graph::EdgeMap<T>, typename CapMap=typename Graph::EdgeMap<T>,
48 typename IntMap=typename Graph::NodeMap<int>, typename TMap=typename Graph::NodeMap<T> >
51 typedef typename Graph::NodeIt NodeIt;
52 typedef typename Graph::EdgeIt EdgeIt;
53 typedef typename Graph::EachNodeIt EachNodeIt;
54 typedef typename Graph::OutEdgeIt OutEdgeIt;
55 typedef typename Graph::InEdgeIt InEdgeIt;
66 preflow_hl2(Graph& _G, NodeIt _s, NodeIt _t, CapMap& _capacity) :
67 G(_G), s(_s), t(_t), flow(_G, 0), capacity(_capacity) { }
76 b is a bound on the highest level of an active node.
77 In the beginning it is at most n-2.
83 std::vector<int> numb(n);
85 The number of nodes on level i < n. It is
86 initialized to n+1, because of the reverse_bfs-part.
89 std::vector<std::stack<NodeIt> > stack(2*n-1);
90 //Stack of the active nodes in level i.
93 /*Reverse_bfs from t, to find the starting level.*/
95 std::queue<NodeIt> bfs_queue;
98 while (!bfs_queue.empty()) {
100 NodeIt v=bfs_queue.front();
102 int l=level.get(v)+1;
104 for(InEdgeIt e=G.template first<InEdgeIt>(v); e.valid(); ++e) {
106 if ( level.get(w) == n ) {
118 /* Starting flow. It is everywhere 0 at the moment. */
119 for(OutEdgeIt e=G.template first<OutEdgeIt>(s); e.valid(); ++e)
122 if ( c == 0 ) continue;
125 if ( excess.get(w) == 0 && w!=t ) stack[level.get(w)].push(w);
127 excess.set(w, excess.get(w)+c);
138 Push/relabel on the highest level active nodes.
140 /*While there exists an active node.*/
142 if ( stack[b].empty() ) {
144 if ( !no_end ) break;
155 NodeIt w=stack[b].top(); //w is a highest label active node.
157 int lev=level.get(w);
158 int exc=excess.get(w);
159 int newlevel=2*n; //In newlevel we bound the next level of w.
161 // if ( level.get(w) < n ) { //Nem tudom ez mukodik-e
162 for(OutEdgeIt e=G.template first<OutEdgeIt>(w); e.valid(); ++e) {
164 if ( flow.get(e) == capacity.get(e) ) continue;
168 if( lev > level.get(v) ) {
169 /*Push is allowed now*/
171 if ( excess.get(v)==0 && v != s && v !=t )
172 stack[level.get(v)].push(v);
173 /*v becomes active.*/
175 int cap=capacity.get(e);
179 if ( remcap >= exc ) {
180 /*A nonsaturating push.*/
182 flow.set(e, flo+exc);
183 excess.set(v, excess.get(v)+exc);
188 /*A saturating push.*/
191 excess.set(v, excess.get(v)+remcap);
194 } else if ( newlevel > level.get(v) ) newlevel = level.get(v);
200 for( InEdgeIt e=G.template first<InEdgeIt>(w); e.valid(); ++e) {
202 if( flow.get(e) == 0 ) continue;
206 if( lev > level.get(v) ) {
207 /*Push is allowed now*/
209 if ( excess.get(v)==0 && v != s && v !=t)
210 stack[level.get(v)].push(v);
211 /*v becomes active.*/
216 /*A nonsaturating push.*/
218 flow.set(e, flo-exc);
219 excess.set(v, excess.get(v)+exc);
223 /*A saturating push.*/
225 excess.set(v, excess.get(v)+flo);
229 } else if ( newlevel > level.get(v) ) newlevel = level.get(v);
233 } // if w still has excess after the out edge for cycle
243 //now 'lev' is the old level of w
244 level.set(w,++newlevel);
249 if ( !numb[lev] && lev < A*n ) { //If the level of w gets empty.
251 for (EachNodeIt v=G.template first<EachNodeIt>(); v.valid() ; ++v) {
252 if (level.get(v) > lev && level.get(v) < n ) level.set(v,n);
254 for (int i=lev+1 ; i!=n ; ++i) numb[i]=0;
255 if ( newlevel < n ) newlevel=n;
257 if ( newlevel < n ) ++numb[newlevel];
261 stack[newlevel].push(w);
265 } // if stack[b] is nonempty
270 value = excess.get(t);
281 Returns the maximum value of a flow.
291 For the maximum flow x found by the algorithm, it returns the flow value on Edge e, i.e. x(e).
294 T flowonedge(EdgeIt e) {
301 Returns the maximum flow x found by the algorithm.
312 Returns the minimum min cut, by a bfs from s in the residual graph.
315 template<typename CutMap>
316 void mincut(CutMap& M) {
318 std::queue<NodeIt> queue;
323 while (!queue.empty()) {
324 NodeIt w=queue.front();
327 for(OutEdgeIt e=G.template first<OutEdgeIt>(w) ; e.valid(); ++e) {
329 if (!M.get(v) && flow.get(e) < capacity.get(e) ) {
335 for(InEdgeIt e=G.template first<InEdgeIt>(w) ; e.valid(); ++e) {
337 if (!M.get(v) && flow.get(e) > 0 ) {
350 Returns the maximum min cut, by a reverse bfs
351 from t in the residual graph.
354 template<typename CutMap>
355 void max_mincut(CutMap& M) {
357 std::queue<NodeIt> queue;
362 while (!queue.empty()) {
363 NodeIt w=queue.front();
366 for(InEdgeIt e=G.template first<InEdgeIt>(w) ; e.valid(); ++e) {
368 if (!M.get(v) && flow.get(e) < capacity.get(e) ) {
374 for(OutEdgeIt e=G.template first<OutEdgeIt>(w) ; e.valid(); ++e) {
376 if (!M.get(v) && flow.get(e) > 0 ) {
383 for(EachNodeIt v=G.template first<EachNodeIt>() ; v.valid(); ++v) {
391 template<typename CutMap>
392 void min_mincut(CutMap& M) {