[Lemon-commits] Peter Kovacs: Port cycle canceling algorithms fr...
Lemon HG
hg at lemon.cs.elte.hu
Mon Dec 14 06:17:45 CET 2009
details: http://lemon.cs.elte.hu/hg/lemon/rev/0643a9c2c3ae
changeset: 880:0643a9c2c3ae
user: Peter Kovacs <kpeter [at] inf.elte.hu>
date: Fri Nov 13 00:09:35 2009 +0100
description:
Port cycle canceling algorithms from SVN -r3524 (#180)
diffstat:
lemon/Makefile.am | 2 +
lemon/cancel_and_tighten.h | 797 ++++++++++++++++++++++++++++++++++++++++++++++
lemon/cycle_canceling.h | 559 ++++++++++++++++++++++++++++++++
3 files changed, 1358 insertions(+), 0 deletions(-)
diffs (truncated from 1385 to 300 lines):
diff --git a/lemon/Makefile.am b/lemon/Makefile.am
--- a/lemon/Makefile.am
+++ b/lemon/Makefile.am
@@ -62,6 +62,7 @@
lemon/bin_heap.h \
lemon/binom_heap.h \
lemon/bucket_heap.h \
+ lemon/cancel_and_tighten.h \
lemon/capacity_scaling.h \
lemon/cbc.h \
lemon/circulation.h \
@@ -73,6 +74,7 @@
lemon/cost_scaling.h \
lemon/counter.h \
lemon/cplex.h \
+ lemon/cycle_canceling.h \
lemon/dfs.h \
lemon/dijkstra.h \
lemon/dim2.h \
diff --git a/lemon/cancel_and_tighten.h b/lemon/cancel_and_tighten.h
new file mode 100644
--- /dev/null
+++ b/lemon/cancel_and_tighten.h
@@ -0,0 +1,797 @@
+/* -*- C++ -*-
+ *
+ * This file is a part of LEMON, a generic C++ optimization library
+ *
+ * Copyright (C) 2003-2008
+ * Egervary Jeno Kombinatorikus Optimalizalasi Kutatocsoport
+ * (Egervary Research Group on Combinatorial Optimization, EGRES).
+ *
+ * Permission to use, modify and distribute this software is granted
+ * provided that this copyright notice appears in all copies. For
+ * precise terms see the accompanying LICENSE file.
+ *
+ * This software is provided "AS IS" with no warranty of any kind,
+ * express or implied, and with no claim as to its suitability for any
+ * purpose.
+ *
+ */
+
+#ifndef LEMON_CANCEL_AND_TIGHTEN_H
+#define LEMON_CANCEL_AND_TIGHTEN_H
+
+/// \ingroup min_cost_flow
+///
+/// \file
+/// \brief Cancel and Tighten algorithm for finding a minimum cost flow.
+
+#include <vector>
+
+#include <lemon/circulation.h>
+#include <lemon/bellman_ford.h>
+#include <lemon/howard.h>
+#include <lemon/adaptors.h>
+#include <lemon/tolerance.h>
+#include <lemon/math.h>
+
+#include <lemon/static_graph.h>
+
+namespace lemon {
+
+ /// \addtogroup min_cost_flow
+ /// @{
+
+ /// \brief Implementation of the Cancel and Tighten algorithm for
+ /// finding a minimum cost flow.
+ ///
+ /// \ref CancelAndTighten implements the Cancel and Tighten algorithm for
+ /// finding a minimum cost flow.
+ ///
+ /// \tparam Digraph The digraph type the algorithm runs on.
+ /// \tparam LowerMap The type of the lower bound map.
+ /// \tparam CapacityMap The type of the capacity (upper bound) map.
+ /// \tparam CostMap The type of the cost (length) map.
+ /// \tparam SupplyMap The type of the supply map.
+ ///
+ /// \warning
+ /// - Arc capacities and costs should be \e non-negative \e integers.
+ /// - Supply values should be \e signed \e integers.
+ /// - The value types of the maps should be convertible to each other.
+ /// - \c CostMap::Value must be signed type.
+ ///
+ /// \author Peter Kovacs
+ template < typename Digraph,
+ typename LowerMap = typename Digraph::template ArcMap<int>,
+ typename CapacityMap = typename Digraph::template ArcMap<int>,
+ typename CostMap = typename Digraph::template ArcMap<int>,
+ typename SupplyMap = typename Digraph::template NodeMap<int> >
+ class CancelAndTighten
+ {
+ TEMPLATE_DIGRAPH_TYPEDEFS(Digraph);
+
+ typedef typename CapacityMap::Value Capacity;
+ typedef typename CostMap::Value Cost;
+ typedef typename SupplyMap::Value Supply;
+ typedef typename Digraph::template ArcMap<Capacity> CapacityArcMap;
+ typedef typename Digraph::template NodeMap<Supply> SupplyNodeMap;
+
+ typedef ResidualDigraph< const Digraph,
+ CapacityArcMap, CapacityArcMap > ResDigraph;
+
+ public:
+
+ /// The type of the flow map.
+ typedef typename Digraph::template ArcMap<Capacity> FlowMap;
+ /// The type of the potential map.
+ typedef typename Digraph::template NodeMap<Cost> PotentialMap;
+
+ private:
+
+ /// \brief Map adaptor class for handling residual arc costs.
+ ///
+ /// Map adaptor class for handling residual arc costs.
+ class ResidualCostMap : public MapBase<typename ResDigraph::Arc, Cost>
+ {
+ typedef typename ResDigraph::Arc Arc;
+
+ private:
+
+ const CostMap &_cost_map;
+
+ public:
+
+ ///\e
+ ResidualCostMap(const CostMap &cost_map) : _cost_map(cost_map) {}
+
+ ///\e
+ Cost operator[](const Arc &e) const {
+ return ResDigraph::forward(e) ? _cost_map[e] : -_cost_map[e];
+ }
+
+ }; //class ResidualCostMap
+
+ /// \brief Map adaptor class for handling reduced arc costs.
+ ///
+ /// Map adaptor class for handling reduced arc costs.
+ class ReducedCostMap : public MapBase<Arc, Cost>
+ {
+ private:
+
+ const Digraph &_gr;
+ const CostMap &_cost_map;
+ const PotentialMap &_pot_map;
+
+ public:
+
+ ///\e
+ ReducedCostMap( const Digraph &gr,
+ const CostMap &cost_map,
+ const PotentialMap &pot_map ) :
+ _gr(gr), _cost_map(cost_map), _pot_map(pot_map) {}
+
+ ///\e
+ inline Cost operator[](const Arc &e) const {
+ return _cost_map[e] + _pot_map[_gr.source(e)]
+ - _pot_map[_gr.target(e)];
+ }
+
+ }; //class ReducedCostMap
+
+ struct BFOperationTraits {
+ static double zero() { return 0; }
+
+ static double infinity() {
+ return std::numeric_limits<double>::infinity();
+ }
+
+ static double plus(const double& left, const double& right) {
+ return left + right;
+ }
+
+ static bool less(const double& left, const double& right) {
+ return left + 1e-6 < right;
+ }
+ }; // class BFOperationTraits
+
+ private:
+
+ // The digraph the algorithm runs on
+ const Digraph &_graph;
+ // The original lower bound map
+ const LowerMap *_lower;
+ // The modified capacity map
+ CapacityArcMap _capacity;
+ // The original cost map
+ const CostMap &_cost;
+ // The modified supply map
+ SupplyNodeMap _supply;
+ bool _valid_supply;
+
+ // Arc map of the current flow
+ FlowMap *_flow;
+ bool _local_flow;
+ // Node map of the current potentials
+ PotentialMap *_potential;
+ bool _local_potential;
+
+ // The residual digraph
+ ResDigraph *_res_graph;
+ // The residual cost map
+ ResidualCostMap _res_cost;
+
+ public:
+
+ /// \brief General constructor (with lower bounds).
+ ///
+ /// General constructor (with lower bounds).
+ ///
+ /// \param digraph The digraph the algorithm runs on.
+ /// \param lower The lower bounds of the arcs.
+ /// \param capacity The capacities (upper bounds) of the arcs.
+ /// \param cost The cost (length) values of the arcs.
+ /// \param supply The supply values of the nodes (signed).
+ CancelAndTighten( const Digraph &digraph,
+ const LowerMap &lower,
+ const CapacityMap &capacity,
+ const CostMap &cost,
+ const SupplyMap &supply ) :
+ _graph(digraph), _lower(&lower), _capacity(digraph), _cost(cost),
+ _supply(digraph), _flow(NULL), _local_flow(false),
+ _potential(NULL), _local_potential(false),
+ _res_graph(NULL), _res_cost(_cost)
+ {
+ // Check the sum of supply values
+ Supply sum = 0;
+ for (NodeIt n(_graph); n != INVALID; ++n) {
+ _supply[n] = supply[n];
+ sum += _supply[n];
+ }
+ _valid_supply = sum == 0;
+
+ // Remove non-zero lower bounds
+ for (ArcIt e(_graph); e != INVALID; ++e) {
+ _capacity[e] = capacity[e];
+ if (lower[e] != 0) {
+ _capacity[e] -= lower[e];
+ _supply[_graph.source(e)] -= lower[e];
+ _supply[_graph.target(e)] += lower[e];
+ }
+ }
+ }
+/*
+ /// \brief General constructor (without lower bounds).
+ ///
+ /// General constructor (without lower bounds).
+ ///
+ /// \param digraph The digraph the algorithm runs on.
+ /// \param capacity The capacities (upper bounds) of the arcs.
+ /// \param cost The cost (length) values of the arcs.
+ /// \param supply The supply values of the nodes (signed).
+ CancelAndTighten( const Digraph &digraph,
+ const CapacityMap &capacity,
+ const CostMap &cost,
+ const SupplyMap &supply ) :
+ _graph(digraph), _lower(NULL), _capacity(capacity), _cost(cost),
+ _supply(supply), _flow(NULL), _local_flow(false),
+ _potential(NULL), _local_potential(false),
+ _res_graph(NULL), _res_cost(_cost)
+ {
+ // Check the sum of supply values
+ Supply sum = 0;
+ for (NodeIt n(_graph); n != INVALID; ++n) sum += _supply[n];
+ _valid_supply = sum == 0;
+ }
+
+ /// \brief Simple constructor (with lower bounds).
+ ///
+ /// Simple constructor (with lower bounds).
+ ///
+ /// \param digraph The digraph the algorithm runs on.
+ /// \param lower The lower bounds of the arcs.
+ /// \param capacity The capacities (upper bounds) of the arcs.
+ /// \param cost The cost (length) values of the arcs.
+ /// \param s The source node.
+ /// \param t The target node.
+ /// \param flow_value The required amount of flow from node \c s
+ /// to node \c t (i.e. the supply of \c s and the demand of \c t).
+ CancelAndTighten( const Digraph &digraph,
+ const LowerMap &lower,
+ const CapacityMap &capacity,
+ const CostMap &cost,
+ Node s, Node t,
+ Supply flow_value ) :
+ _graph(digraph), _lower(&lower), _capacity(capacity), _cost(cost),
+ _supply(digraph, 0), _flow(NULL), _local_flow(false),
+ _potential(NULL), _local_potential(false),
+ _res_graph(NULL), _res_cost(_cost)
+ {
+ // Remove non-zero lower bounds
+ _supply[s] = flow_value;
+ _supply[t] = -flow_value;
+ for (ArcIt e(_graph); e != INVALID; ++e) {
+ if (lower[e] != 0) {
+ _capacity[e] -= lower[e];
+ _supply[_graph.source(e)] -= lower[e];
+ _supply[_graph.target(e)] += lower[e];
+ }
+ }
More information about the Lemon-commits
mailing list