# HG changeset patch # User marci # Date 1075474144 0 # Node ID 8ff5dc7d18eb29239daece5fbd072f4d3b286143 # Parent 3ee2187d6342231d41d9d9e655d0f8d93f8daa87 marci_max_flow.hh in the new concept diff -r 3ee2187d6342 -r 8ff5dc7d18eb src/work/edmonds_karp.hh --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/src/work/edmonds_karp.hh Fri Jan 30 14:49:04 2004 +0000 @@ -0,0 +1,206 @@ +#ifndef MARCI_MAX_FLOW_HH +#define MARCI_MAX_FLOW_HH + +#include + +#include + +namespace marci { + + template + class ResGraph { + typedef typename Graph::NodeIt NodeIt; + typedef typename Graph::EachNodeIt EachNodeIt; + typedef typename Graph::SymEdgeIt OldSymEdgeIt; + const Graph& G; + typename Graph::EdgeMap& flow; + const typename Graph::EdgeMap& capacity; + public: + ResGraph(const Graph& _G, typename Graph::EdgeMap& _flow, + const typename Graph::EdgeMap& _capacity) : + G(_G), flow(_flow), capacity(_capacity) { } + + class EdgeIt; + class OutEdgeIt; + friend class EdgeIt; + friend class OutEdgeIt; + + class EdgeIt { + friend class ResGraph; + protected: + const ResGraph* resG; + OldSymEdgeIt sym; + public: + EdgeIt() { } + //EdgeIt(const EdgeIt& e) : resG(e.resG), sym(e.sym) { } + T free() const { + if (resG->G.aNode(sym)==resG->G.tail(sym)) { + return (resG->capacity.get(sym)-resG->flow.get(sym)); + } else { + return (resG->flow.get(sym)); + } + } + bool valid() const { return sym.valid(); } + void augment(const T a) const { + if (resG->G.aNode(sym)==resG->G.tail(sym)) { + resG->flow.set(sym, resG->flow.get(sym)+a); + } else { + resG->flow.set(sym, resG->flow.get(sym)-a); + } + } + }; + + class OutEdgeIt : public EdgeIt { + friend class ResGraph; + public: + OutEdgeIt() { } + //OutEdgeIt(const OutEdgeIt& e) { resG=e.resG; sym=e.sym; } + private: + OutEdgeIt(const ResGraph& _resG, const NodeIt v) { + resG=&_resG; + sym=resG->G.template first(v); + while( sym.valid() && !(free()>0) ) { ++sym; } + } + public: + OutEdgeIt& operator++() { + ++sym; + while( sym.valid() && !(free()>0) ) { ++sym; } + return *this; + } + }; + + void getFirst(OutEdgeIt& e, const NodeIt v) const { + e=OutEdgeIt(*this, v); + } + void getFirst(EachNodeIt& v) const { G.getFirst(v); } + + template< typename It > + It first() const { + It e; + getFirst(e); + return e; + } + + template< typename It > + It first(const NodeIt v) const { + It e; + getFirst(e, v); + return e; + } + + NodeIt tail(const EdgeIt e) const { return G.aNode(e.sym); } + NodeIt head(const EdgeIt e) const { return G.bNode(e.sym); } + + NodeIt aNode(const OutEdgeIt e) const { return G.aNode(e.sym); } + NodeIt bNode(const OutEdgeIt e) const { return G.bNode(e.sym); } + + int id(const NodeIt v) const { return G.id(v); } + + template + class NodeMap { + //const ResGraph& G; + typename Graph::NodeMap node_map; + public: + NodeMap(const ResGraph& _G) : node_map(_G.G)/*: G(_G)*/ { } + NodeMap(const ResGraph& _G, const ValueType a) : node_map(_G.G, a) /*: G(_G)*/ { } + void set(const NodeIt nit, const ValueType a) { node_map.set(nit, a); } + ValueType get(const NodeIt nit) const { return node_map.get(nit); } + }; + + }; + + template + struct max_flow_type { + typedef typename Graph::NodeIt NodeIt; + typedef typename Graph::EdgeIt EdgeIt; + typedef typename Graph::EachEdgeIt EachEdgeIt; + typedef typename Graph::OutEdgeIt OutEdgeIt; + typedef typename Graph::InEdgeIt InEdgeIt; + const Graph& G; + NodeIt s; + NodeIt t; + typename Graph::EdgeMap flow; + const typename Graph::EdgeMap& capacity; + + max_flow_type(const Graph& _G, NodeIt _s, NodeIt _t, const typename Graph::EdgeMap& _capacity) : G(_G), s(_s), t(_t), flow(_G, 0), capacity(_capacity) { } + void run() { + typedef ResGraph AugGraph; + AugGraph res_graph(G, flow, capacity); + + bool augment; + do { + augment=false; + + typedef typename AugGraph::OutEdgeIt AugOutEdgeIt; + typedef typename AugGraph::EdgeIt AugEdgeIt; + typedef std::queue BfsQueue; + BfsQueue bfs_queue; + bfs_queue.push(res_graph.template first(s)); + + typedef typename AugGraph::NodeMap ReachedMap; + ReachedMap reached(res_graph, false); + reached.set(s, true); + + bfs_iterator1< AugGraph, ReachedMap > + res_bfs(res_graph, bfs_queue, reached); + + typedef typename AugGraph::NodeMap PredMap; + PredMap pred(res_graph); + //typename AugGraph::EdgeIt a; //invalid + //a.makeInvalid(); + //pred.set(s, a); + + typedef typename AugGraph::NodeMap FreeMap; + FreeMap free(res_graph); + + //searching for augmenting path + while ( res_bfs.valid() ) { + //std::cout<<"KULSO ciklus itt jar: "<"<"<"<(); e.valid(); ++e) { + std::cout<<"("<"<