Changeset 2340:03c71d754990 in lemon-0.x for lemon/hao_orlin.h
- Timestamp:
- 01/11/07 22:22:39 (17 years ago)
- Branch:
- default
- Phase:
- public
- Convert:
- svn:c9d7d8f5-90d6-0310-b91f-818b3a526b0e/lemon/trunk@3132
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
lemon/hao_orlin.h
r2275 r2340 20 20 #define LEMON_HAO_ORLIN_H 21 21 22 #include <cassert> 23 24 25 22 26 #include <vector> 23 27 #include <queue> 28 #include <list> 24 29 #include <limits> 25 30 … … 28 33 #include <lemon/graph_adaptor.h> 29 34 #include <lemon/iterable_maps.h> 30 31 35 32 36 /// \file … … 109 113 OutResGraph* _out_res_graph; 110 114 111 typedef typename Graph::template NodeMap<OutResEdge> OutCurrentEdgeMap;112 OutCurrentEdgeMap* _out_current_edge;113 114 115 typedef RevGraphAdaptor<const Graph> RevGraph; 115 116 RevGraph* _rev_graph; … … 120 121 121 122 InResGraph* _in_res_graph; 122 123 typedef typename Graph::template NodeMap<InResEdge> InCurrentEdgeMap;124 InCurrentEdgeMap* _in_current_edge;125 126 123 127 124 typedef IterableBoolMap<Graph, Node> WakeMap; … … 162 159 _graph(&graph), _capacity(&capacity), 163 160 _preflow(0), _source(), _target(), 164 _out_res_graph(0), _out_current_edge(0), 165 _rev_graph(0), _in_res_graph(0), _in_current_edge(0), 161 _out_res_graph(0), _rev_graph(0), _in_res_graph(0), 166 162 _wake(0),_dist(0), _excess(0), _source_set(0), 167 163 _highest_active(), _active_nodes(), _dormant_max(), _dormant(), … … 172 168 delete _min_cut_map; 173 169 } 174 if (_in_current_edge) {175 delete _in_current_edge;176 }177 170 if (_in_res_graph) { 178 171 delete _in_res_graph; … … 181 174 delete _rev_graph; 182 175 } 183 if (_out_current_edge) {184 delete _out_current_edge;185 }186 176 if (_out_res_graph) { 187 177 delete _out_res_graph; … … 206 196 private: 207 197 208 template <typename ResGraph , typename EdgeMap>209 void findMinCut(const Node& target, bool out, 210 ResGraph& res_graph, EdgeMap& current_edge) {198 template <typename ResGraph> 199 void findMinCut(const Node& target, bool out, ResGraph& res_graph) { 200 typedef typename Graph::Node Node; 211 201 typedef typename ResGraph::Edge ResEdge; 212 202 typedef typename ResGraph::OutEdgeIt ResOutEdgeIt; … … 220 210 (*_excess)[it] = 0; 221 211 (*_source_set)[it] = false; 222 223 res_graph.firstOut(current_edge[it], it); 224 } 212 } 213 214 _dormant[0].push_front(_source); 215 (*_source_set)[_source] = true; 216 _dormant_max = 0; 217 (*_wake)[_source] = false; 218 219 _level_size[0] = 1; 220 _level_size[1] = _node_num - 1; 225 221 226 222 _target = target; … … 229 225 for (ResOutEdgeIt it(res_graph, _source); it != INVALID; ++it) { 230 226 Value delta = res_graph.rescap(it); 231 if (!_tolerance.positive(delta)) continue; 232 233 (*_excess)[res_graph.source(it)] -= delta; 227 (*_excess)[_source] -= delta; 234 228 res_graph.augment(it, delta); 235 229 Node a = res_graph.target(it); 236 if (!_tolerance.positive((*_excess)[a]) && 237 (*_wake)[a] && a != _target) { 230 if ((*_excess)[a] == 0 && (*_wake)[a] && a != _target) { 238 231 _active_nodes[(*_dist)[a]].push_front(a); 239 232 if (_highest_active < (*_dist)[a]) { … … 244 237 } 245 238 246 _dormant[0].push_front(_source);247 (*_source_set)[_source] = true;248 _dormant_max = 0;249 (*_wake)[_source] = false;250 251 _level_size[0] = 1;252 _level_size[1] = _node_num - 1;253 239 254 240 do { 255 241 Node n; 256 242 while ((n = findActiveNode()) != INVALID) { 257 ResEdge e; 258 while (_tolerance.positive((*_excess)[n]) && 259 (e = findAdmissibleEdge(n, res_graph, current_edge)) 260 != INVALID){ 261 Value delta; 262 if ((*_excess)[n] < res_graph.rescap(e)) { 243 for (ResOutEdgeIt e(res_graph, n); e != INVALID; ++e) { 244 Node a = res_graph.target(e); 245 if ((*_dist)[a] >= (*_dist)[n] || !(*_wake)[a]) continue; 246 Value delta = res_graph.rescap(e); 247 if (_tolerance.positive((*_excess)[n] - delta)) { 248 (*_excess)[n] -= delta; 249 } else { 263 250 delta = (*_excess)[n]; 264 } else { 265 delta = res_graph.rescap(e); 266 res_graph.nextOut(current_edge[n]); 251 (*_excess)[n] = 0; 267 252 } 268 if (!_tolerance.positive(delta)) continue;269 253 res_graph.augment(e, delta); 270 (*_excess)[res_graph.source(e)] -= delta; 271 Node a = res_graph.target(e); 272 if (!_tolerance.positive((*_excess)[a]) && a != _target) { 254 if ((*_excess)[a] == 0 && a != _target) { 273 255 _active_nodes[(*_dist)[a]].push_front(a); 274 256 } 275 257 (*_excess)[a] += delta; 258 if ((*_excess)[n] == 0) break; 276 259 } 277 if ( _tolerance.positive((*_excess)[n])) {278 relabel(n, res_graph , current_edge);260 if ((*_excess)[n] != 0) { 261 relabel(n, res_graph); 279 262 } 280 263 } … … 298 281 } 299 282 300 template <typename ResGraph , typename EdgeMap>301 void relabel(const Node& n, ResGraph& res_graph , EdgeMap& current_edge) {283 template <typename ResGraph> 284 void relabel(const Node& n, ResGraph& res_graph) { 302 285 typedef typename ResGraph::OutEdgeIt ResOutEdgeIt; 303 286 … … 312 295 } 313 296 } 314 297 --_highest_active; 315 298 } else { 316 299 int new_dist = _node_num; … … 332 315 _active_nodes[_highest_active].push_front(n); 333 316 ++_level_size[(*_dist)[n]]; 334 res_graph.firstOut(current_edge[n], n);335 317 } 336 318 } … … 373 355 if (wake_was_empty){ 374 356 for (typename WakeMap::TrueIt it(*_wake); it != INVALID; ++it) { 375 if (_tolerance.positive((*_excess)[it])) { 376 if ((*_wake)[it] && it != _target) { 377 _active_nodes[(*_dist)[it]].push_front(it); 378 } 379 if (_highest_active < (*_dist)[it]) { 380 _highest_active = (*_dist)[it]; 357 if ((*_excess)[it] != 0 && it != _target) { 358 _active_nodes[(*_dist)[it]].push_front(it); 359 if (_highest_active < (*_dist)[it]) { 360 _highest_active = (*_dist)[it]; 381 361 } 382 362 } … … 384 364 } 385 365 386 for (ResOutEdgeIt e(res_graph, old_target); e!=INVALID; ++e){ 387 if (!(*_source_set)[res_graph.target(e)]) { 388 Value delta = res_graph.rescap(e); 389 if (!_tolerance.positive(delta)) continue; 390 res_graph.augment(e, delta); 391 (*_excess)[res_graph.source(e)] -= delta; 392 Node a = res_graph.target(e); 393 if (!_tolerance.positive((*_excess)[a]) && 394 (*_wake)[a] && a != _target) { 395 _active_nodes[(*_dist)[a]].push_front(a); 396 if (_highest_active < (*_dist)[a]) { 397 _highest_active = (*_dist)[a]; 398 } 366 Node n = old_target; 367 for (ResOutEdgeIt e(res_graph, n); e != INVALID; ++e){ 368 Node a = res_graph.target(e); 369 if (!(*_wake)[a]) continue; 370 Value delta = res_graph.rescap(e); 371 res_graph.augment(e, delta); 372 (*_excess)[n] -= delta; 373 if ((*_excess)[a] == 0 && (*_wake)[a] && a != _target) { 374 _active_nodes[(*_dist)[a]].push_front(a); 375 if (_highest_active < (*_dist)[a]) { 376 _highest_active = (*_dist)[a]; 399 377 } 400 (*_excess)[a] += delta;401 } 378 } 379 (*_excess)[a] += delta; 402 380 } 403 381 404 382 return true; 405 383 } 406 384 407 385 Node findActiveNode() { 408 386 while (_highest_active > 0 && _active_nodes[_highest_active].empty()){ … … 413 391 _active_nodes[_highest_active].pop_front(); 414 392 return n; 415 } else {416 return INVALID;417 }418 }419 420 template <typename ResGraph, typename EdgeMap>421 typename ResGraph::Edge findAdmissibleEdge(const Node& n,422 ResGraph& res_graph,423 EdgeMap& current_edge) {424 typedef typename ResGraph::Edge ResEdge;425 ResEdge e = current_edge[n];426 while (e != INVALID &&427 ((*_dist)[n] <= (*_dist)[res_graph.target(e)] ||428 !(*_wake)[res_graph.target(e)])) {429 res_graph.nextOut(e);430 }431 if (e != INVALID) {432 current_edge[n] = e;433 return e;434 393 } else { 435 394 return INVALID; … … 513 472 _out_res_graph = new OutResGraph(*_graph, *_capacity, *_preflow); 514 473 } 515 if (!_out_current_edge) {516 _out_current_edge = new OutCurrentEdgeMap(*_graph);517 }518 474 if (!_rev_graph) { 519 475 _rev_graph = new RevGraph(*_graph); … … 521 477 if (!_in_res_graph) { 522 478 _in_res_graph = new InResGraph(*_rev_graph, *_capacity, *_preflow); 523 }524 if (!_in_current_edge) {525 _in_current_edge = new InCurrentEdgeMap(*_graph);526 479 } 527 480 if (!_min_cut_map) { … … 556 509 /// for the push-relabel algorithm. 557 510 void calculateOut(const Node& target) { 558 findMinCut(target, true, *_out_res_graph , *_out_current_edge);511 findMinCut(target, true, *_out_res_graph); 559 512 } 560 513 … … 584 537 /// target for the push-relabel algorithm. 585 538 void calculateIn(const Node& target) { 586 findMinCut(target, false, *_in_res_graph , *_in_current_edge);539 findMinCut(target, false, *_in_res_graph); 587 540 } 588 541
Note: See TracChangeset
for help on using the changeset viewer.