3 * This file is a part of LEMON, a generic C++ optimization library
5 * Copyright (C) 2003-2008
6 * Egervary Jeno Kombinatorikus Optimalizalasi Kutatocsoport
7 * (Egervary Research Group on Combinatorial Optimization, EGRES).
9 * Permission to use, modify and distribute this software is granted
10 * provided that this copyright notice appears in all copies. For
11 * precise terms see the accompanying LICENSE file.
13 * This software is provided "AS IS" with no warranty of any kind,
14 * express or implied, and with no claim as to its suitability for any
19 #ifndef LEMON_COST_SCALING_H
20 #define LEMON_COST_SCALING_H
22 /// \ingroup min_cost_flow
25 /// \brief Cost scaling algorithm for finding a minimum cost flow.
28 #include <lemon/graph_adaptor.h>
29 #include <lemon/graph_utils.h>
30 #include <lemon/maps.h>
31 #include <lemon/math.h>
33 #include <lemon/circulation.h>
34 #include <lemon/bellman_ford.h>
38 /// \addtogroup min_cost_flow
41 /// \brief Implementation of the cost scaling algorithm for finding a
42 /// minimum cost flow.
44 /// \ref CostScaling implements the cost scaling algorithm performing
45 /// generalized push-relabel operations for finding a minimum cost
48 /// \tparam Graph The directed graph type the algorithm runs on.
49 /// \tparam LowerMap The type of the lower bound map.
50 /// \tparam CapacityMap The type of the capacity (upper bound) map.
51 /// \tparam CostMap The type of the cost (length) map.
52 /// \tparam SupplyMap The type of the supply map.
55 /// - Edge capacities and costs should be \e non-negative \e integers.
56 /// - Supply values should be \e signed \e integers.
57 /// - The value types of the maps should be convertible to each other.
58 /// - \c CostMap::Value must be signed type.
60 /// \note Edge costs are multiplied with the number of nodes during
61 /// the algorithm so overflow problems may arise more easily than with
62 /// other minimum cost flow algorithms.
63 /// If it is available, <tt>long long int</tt> type is used instead of
64 /// <tt>long int</tt> in the inside computations.
66 /// \author Peter Kovacs
67 template < typename Graph,
68 typename LowerMap = typename Graph::template EdgeMap<int>,
69 typename CapacityMap = typename Graph::template EdgeMap<int>,
70 typename CostMap = typename Graph::template EdgeMap<int>,
71 typename SupplyMap = typename Graph::template NodeMap<int> >
74 GRAPH_TYPEDEFS(typename Graph);
76 typedef typename CapacityMap::Value Capacity;
77 typedef typename CostMap::Value Cost;
78 typedef typename SupplyMap::Value Supply;
79 typedef typename Graph::template EdgeMap<Capacity> CapacityEdgeMap;
80 typedef typename Graph::template NodeMap<Supply> SupplyNodeMap;
82 typedef ResGraphAdaptor< const Graph, Capacity,
83 CapacityEdgeMap, CapacityEdgeMap > ResGraph;
84 typedef typename ResGraph::Edge ResEdge;
86 #if defined __GNUC__ && !defined __STRICT_ANSI__
87 typedef long long int LCost;
89 typedef long int LCost;
91 typedef typename Graph::template EdgeMap<LCost> LargeCostMap;
95 /// The type of the flow map.
96 typedef typename Graph::template EdgeMap<Capacity> FlowMap;
97 /// The type of the potential map.
98 typedef typename Graph::template NodeMap<LCost> PotentialMap;
102 /// \brief Map adaptor class for handling residual edge costs.
104 /// Map adaptor class for handling residual edge costs.
105 template <typename Map>
106 class ResidualCostMap : public MapBase<ResEdge, typename Map::Value>
110 const Map &_cost_map;
115 ResidualCostMap(const Map &cost_map) :
116 _cost_map(cost_map) {}
119 typename Map::Value operator[](const ResEdge &e) const {
120 return ResGraph::forward(e) ? _cost_map[e] : -_cost_map[e];
123 }; //class ResidualCostMap
125 /// \brief Map adaptor class for handling reduced edge costs.
127 /// Map adaptor class for handling reduced edge costs.
128 class ReducedCostMap : public MapBase<Edge, LCost>
133 const LargeCostMap &_cost_map;
134 const PotentialMap &_pot_map;
139 ReducedCostMap( const Graph &gr,
140 const LargeCostMap &cost_map,
141 const PotentialMap &pot_map ) :
142 _gr(gr), _cost_map(cost_map), _pot_map(pot_map) {}
145 LCost operator[](const Edge &e) const {
146 return _cost_map[e] + _pot_map[_gr.source(e)]
147 - _pot_map[_gr.target(e)];
150 }; //class ReducedCostMap
155 static const int ALPHA = 4;
157 // Paramters for heuristics
158 static const int BF_HEURISTIC_EPSILON_BOUND = 5000;
159 static const int BF_HEURISTIC_BOUND_FACTOR = 3;
163 // The directed graph the algorithm runs on
165 // The original lower bound map
166 const LowerMap *_lower;
167 // The modified capacity map
168 CapacityEdgeMap _capacity;
169 // The original cost map
170 const CostMap &_orig_cost;
171 // The scaled cost map
173 // The modified supply map
174 SupplyNodeMap _supply;
177 // Edge map of the current flow
180 // Node map of the current potentials
181 PotentialMap *_potential;
182 bool _local_potential;
184 // The residual cost map
185 ResidualCostMap<LargeCostMap> _res_cost;
186 // The residual graph
187 ResGraph *_res_graph;
188 // The reduced cost map
189 ReducedCostMap *_red_cost;
191 SupplyNodeMap _excess;
192 // The epsilon parameter used for cost scaling
197 /// \brief General constructor (with lower bounds).
199 /// General constructor (with lower bounds).
201 /// \param graph The directed graph the algorithm runs on.
202 /// \param lower The lower bounds of the edges.
203 /// \param capacity The capacities (upper bounds) of the edges.
204 /// \param cost The cost (length) values of the edges.
205 /// \param supply The supply values of the nodes (signed).
206 CostScaling( const Graph &graph,
207 const LowerMap &lower,
208 const CapacityMap &capacity,
210 const SupplyMap &supply ) :
211 _graph(graph), _lower(&lower), _capacity(graph), _orig_cost(cost),
212 _cost(graph), _supply(graph), _flow(NULL), _local_flow(false),
213 _potential(NULL), _local_potential(false), _res_cost(_cost),
214 _res_graph(NULL), _red_cost(NULL), _excess(graph, 0)
216 // Removing non-zero lower bounds
217 _capacity = subMap(capacity, lower);
219 for (NodeIt n(_graph); n != INVALID; ++n) {
220 Supply s = supply[n];
221 for (InEdgeIt e(_graph, n); e != INVALID; ++e)
223 for (OutEdgeIt e(_graph, n); e != INVALID; ++e)
228 _valid_supply = sum == 0;
231 /// \brief General constructor (without lower bounds).
233 /// General constructor (without lower bounds).
235 /// \param graph The directed graph the algorithm runs on.
236 /// \param capacity The capacities (upper bounds) of the edges.
237 /// \param cost The cost (length) values of the edges.
238 /// \param supply The supply values of the nodes (signed).
239 CostScaling( const Graph &graph,
240 const CapacityMap &capacity,
242 const SupplyMap &supply ) :
243 _graph(graph), _lower(NULL), _capacity(capacity), _orig_cost(cost),
244 _cost(graph), _supply(supply), _flow(NULL), _local_flow(false),
245 _potential(NULL), _local_potential(false), _res_cost(_cost),
246 _res_graph(NULL), _red_cost(NULL), _excess(graph, 0)
248 // Checking the sum of supply values
250 for (NodeIt n(_graph); n != INVALID; ++n) sum += _supply[n];
251 _valid_supply = sum == 0;
254 /// \brief Simple constructor (with lower bounds).
256 /// Simple constructor (with lower bounds).
258 /// \param graph The directed graph the algorithm runs on.
259 /// \param lower The lower bounds of the edges.
260 /// \param capacity The capacities (upper bounds) of the edges.
261 /// \param cost The cost (length) values of the edges.
262 /// \param s The source node.
263 /// \param t The target node.
264 /// \param flow_value The required amount of flow from node \c s
265 /// to node \c t (i.e. the supply of \c s and the demand of \c t).
266 CostScaling( const Graph &graph,
267 const LowerMap &lower,
268 const CapacityMap &capacity,
271 Supply flow_value ) :
272 _graph(graph), _lower(&lower), _capacity(graph), _orig_cost(cost),
273 _cost(graph), _supply(graph), _flow(NULL), _local_flow(false),
274 _potential(NULL), _local_potential(false), _res_cost(_cost),
275 _res_graph(NULL), _red_cost(NULL), _excess(graph, 0)
277 // Removing nonzero lower bounds
278 _capacity = subMap(capacity, lower);
279 for (NodeIt n(_graph); n != INVALID; ++n) {
281 if (n == s) sum = flow_value;
282 if (n == t) sum = -flow_value;
283 for (InEdgeIt e(_graph, n); e != INVALID; ++e)
285 for (OutEdgeIt e(_graph, n); e != INVALID; ++e)
289 _valid_supply = true;
292 /// \brief Simple constructor (without lower bounds).
294 /// Simple constructor (without lower bounds).
296 /// \param graph The directed graph the algorithm runs on.
297 /// \param capacity The capacities (upper bounds) of the edges.
298 /// \param cost The cost (length) values of the edges.
299 /// \param s The source node.
300 /// \param t The target node.
301 /// \param flow_value The required amount of flow from node \c s
302 /// to node \c t (i.e. the supply of \c s and the demand of \c t).
303 CostScaling( const Graph &graph,
304 const CapacityMap &capacity,
307 Supply flow_value ) :
308 _graph(graph), _lower(NULL), _capacity(capacity), _orig_cost(cost),
309 _cost(graph), _supply(graph, 0), _flow(NULL), _local_flow(false),
310 _potential(NULL), _local_potential(false), _res_cost(_cost),
311 _res_graph(NULL), _red_cost(NULL), _excess(graph, 0)
313 _supply[s] = flow_value;
314 _supply[t] = -flow_value;
315 _valid_supply = true;
320 if (_local_flow) delete _flow;
321 if (_local_potential) delete _potential;
326 /// \brief Set the flow map.
328 /// Set the flow map.
330 /// \return \c (*this)
331 CostScaling& flowMap(FlowMap &map) {
340 /// \brief Set the potential map.
342 /// Set the potential map.
344 /// \return \c (*this)
345 CostScaling& potentialMap(PotentialMap &map) {
346 if (_local_potential) {
348 _local_potential = false;
354 /// \name Execution control
358 /// \brief Run the algorithm.
360 /// Run the algorithm.
362 /// \return \c true if a feasible flow can be found.
364 return init() && start();
369 /// \name Query Functions
370 /// The result of the algorithm can be obtained using these
372 /// \ref lemon::CostScaling::run() "run()" must be called before
377 /// \brief Return a const reference to the edge map storing the
380 /// Return a const reference to the edge map storing the found flow.
382 /// \pre \ref run() must be called before using this function.
383 const FlowMap& flowMap() const {
387 /// \brief Return a const reference to the node map storing the
388 /// found potentials (the dual solution).
390 /// Return a const reference to the node map storing the found
391 /// potentials (the dual solution).
393 /// \pre \ref run() must be called before using this function.
394 const PotentialMap& potentialMap() const {
398 /// \brief Return the flow on the given edge.
400 /// Return the flow on the given edge.
402 /// \pre \ref run() must be called before using this function.
403 Capacity flow(const Edge& edge) const {
404 return (*_flow)[edge];
407 /// \brief Return the potential of the given node.
409 /// Return the potential of the given node.
411 /// \pre \ref run() must be called before using this function.
412 Cost potential(const Node& node) const {
413 return (*_potential)[node];
416 /// \brief Return the total cost of the found flow.
418 /// Return the total cost of the found flow. The complexity of the
419 /// function is \f$ O(e) \f$.
421 /// \pre \ref run() must be called before using this function.
422 Cost totalCost() const {
424 for (EdgeIt e(_graph); e != INVALID; ++e)
425 c += (*_flow)[e] * _orig_cost[e];
433 /// Initialize the algorithm.
435 if (!_valid_supply) return false;
437 // Initializing flow and potential maps
439 _flow = new FlowMap(_graph);
443 _potential = new PotentialMap(_graph);
444 _local_potential = true;
447 _red_cost = new ReducedCostMap(_graph, _cost, *_potential);
448 _res_graph = new ResGraph(_graph, _capacity, *_flow);
450 // Initializing the scaled cost map and the epsilon parameter
452 int node_num = countNodes(_graph);
453 for (EdgeIt e(_graph); e != INVALID; ++e) {
454 _cost[e] = LCost(_orig_cost[e]) * node_num * ALPHA;
455 if (_orig_cost[e] > max_cost) max_cost = _orig_cost[e];
457 _epsilon = max_cost * node_num;
459 // Finding a feasible flow using Circulation
460 Circulation< Graph, ConstMap<Edge, Capacity>, CapacityEdgeMap,
462 circulation( _graph, constMap<Edge>(Capacity(0)), _capacity,
464 return circulation.flowMap(*_flow).run();
468 /// Execute the algorithm.
470 std::deque<Node> active_nodes;
471 typename Graph::template NodeMap<bool> hyper(_graph, false);
473 int node_num = countNodes(_graph);
474 for ( ; _epsilon >= 1; _epsilon = _epsilon < ALPHA && _epsilon > 1 ?
475 1 : _epsilon / ALPHA )
477 // Performing price refinement heuristic using Bellman-Ford
479 if (_epsilon <= BF_HEURISTIC_EPSILON_BOUND) {
480 typedef ShiftMap< ResidualCostMap<LargeCostMap> > ShiftCostMap;
481 ShiftCostMap shift_cost(_res_cost, _epsilon);
482 BellmanFord<ResGraph, ShiftCostMap> bf(*_res_graph, shift_cost);
485 int K = int(BF_HEURISTIC_BOUND_FACTOR * sqrt(node_num));
486 for (int i = 0; i < K && !done; ++i)
487 done = bf.processNextWeakRound();
489 for (NodeIt n(_graph); n != INVALID; ++n)
490 (*_potential)[n] = bf.dist(n);
495 // Saturating edges not satisfying the optimality condition
497 for (EdgeIt e(_graph); e != INVALID; ++e) {
498 if (_capacity[e] - (*_flow)[e] > 0 && (*_red_cost)[e] < 0) {
499 delta = _capacity[e] - (*_flow)[e];
500 _excess[_graph.source(e)] -= delta;
501 _excess[_graph.target(e)] += delta;
502 (*_flow)[e] = _capacity[e];
504 if ((*_flow)[e] > 0 && -(*_red_cost)[e] < 0) {
505 _excess[_graph.target(e)] -= (*_flow)[e];
506 _excess[_graph.source(e)] += (*_flow)[e];
511 // Finding active nodes (i.e. nodes with positive excess)
512 for (NodeIt n(_graph); n != INVALID; ++n)
513 if (_excess[n] > 0) active_nodes.push_back(n);
515 // Performing push and relabel operations
516 while (active_nodes.size() > 0) {
517 Node n = active_nodes[0], t;
518 bool relabel_enabled = true;
520 // Performing push operations if there are admissible edges
521 if (_excess[n] > 0) {
522 for (OutEdgeIt e(_graph, n); e != INVALID; ++e) {
523 if (_capacity[e] - (*_flow)[e] > 0 && (*_red_cost)[e] < 0) {
524 delta = _capacity[e] - (*_flow)[e] <= _excess[n] ?
525 _capacity[e] - (*_flow)[e] : _excess[n];
526 t = _graph.target(e);
528 // Push-look-ahead heuristic
529 Capacity ahead = -_excess[t];
530 for (OutEdgeIt oe(_graph, t); oe != INVALID; ++oe) {
531 if (_capacity[oe] - (*_flow)[oe] > 0 && (*_red_cost)[oe] < 0)
532 ahead += _capacity[oe] - (*_flow)[oe];
534 for (InEdgeIt ie(_graph, t); ie != INVALID; ++ie) {
535 if ((*_flow)[ie] > 0 && -(*_red_cost)[ie] < 0)
536 ahead += (*_flow)[ie];
538 if (ahead < 0) ahead = 0;
540 // Pushing flow along the edge
542 (*_flow)[e] += ahead;
545 active_nodes.push_front(t);
547 relabel_enabled = false;
550 (*_flow)[e] += delta;
553 if (_excess[t] > 0 && _excess[t] <= delta)
554 active_nodes.push_back(t);
557 if (_excess[n] == 0) break;
562 if (_excess[n] > 0) {
563 for (InEdgeIt e(_graph, n); e != INVALID; ++e) {
564 if ((*_flow)[e] > 0 && -(*_red_cost)[e] < 0) {
565 delta = (*_flow)[e] <= _excess[n] ? (*_flow)[e] : _excess[n];
566 t = _graph.source(e);
568 // Push-look-ahead heuristic
569 Capacity ahead = -_excess[t];
570 for (OutEdgeIt oe(_graph, t); oe != INVALID; ++oe) {
571 if (_capacity[oe] - (*_flow)[oe] > 0 && (*_red_cost)[oe] < 0)
572 ahead += _capacity[oe] - (*_flow)[oe];
574 for (InEdgeIt ie(_graph, t); ie != INVALID; ++ie) {
575 if ((*_flow)[ie] > 0 && -(*_red_cost)[ie] < 0)
576 ahead += (*_flow)[ie];
578 if (ahead < 0) ahead = 0;
580 // Pushing flow along the edge
582 (*_flow)[e] -= ahead;
585 active_nodes.push_front(t);
587 relabel_enabled = false;
590 (*_flow)[e] -= delta;
593 if (_excess[t] > 0 && _excess[t] <= delta)
594 active_nodes.push_back(t);
597 if (_excess[n] == 0) break;
602 if (relabel_enabled && (_excess[n] > 0 || hyper[n])) {
603 // Performing relabel operation if the node is still active
604 LCost min_red_cost = std::numeric_limits<LCost>::max();
605 for (OutEdgeIt oe(_graph, n); oe != INVALID; ++oe) {
606 if ( _capacity[oe] - (*_flow)[oe] > 0 &&
607 (*_red_cost)[oe] < min_red_cost )
608 min_red_cost = (*_red_cost)[oe];
610 for (InEdgeIt ie(_graph, n); ie != INVALID; ++ie) {
611 if ((*_flow)[ie] > 0 && -(*_red_cost)[ie] < min_red_cost)
612 min_red_cost = -(*_red_cost)[ie];
614 (*_potential)[n] -= min_red_cost + _epsilon;
618 // Removing active nodes with non-positive excess
619 while ( active_nodes.size() > 0 &&
620 _excess[active_nodes[0]] <= 0 &&
621 !hyper[active_nodes[0]] ) {
622 active_nodes.pop_front();
627 // Computing node potentials for the original costs
628 ResidualCostMap<CostMap> res_cost(_orig_cost);
629 BellmanFord< ResGraph, ResidualCostMap<CostMap> >
630 bf(*_res_graph, res_cost);
631 bf.init(0); bf.start();
632 for (NodeIt n(_graph); n != INVALID; ++n)
633 (*_potential)[n] = bf.dist(n);
635 // Handling non-zero lower bounds
637 for (EdgeIt e(_graph); e != INVALID; ++e)
638 (*_flow)[e] += (*_lower)[e];
643 }; //class CostScaling
649 #endif //LEMON_COST_SCALING_H