marci@764: // -*- c++ -*-
marci@764: #include <iostream>
marci@764: #include <fstream>
marci@764: 
alpar@921: #include <lemon/smart_graph.h>
marci@1014: #include <lemon/list_graph.h>
alpar@921: #include <lemon/dimacs.h>
alpar@921: #include <lemon/time_measure.h>
marci@764: //#include <graph_wrapper.h>
marci@1014: #include <lemon/preflow.h>
marci@764: #include <augmenting_flow.h>
marci@764: //#include <preflow_res.h>
marci@1031: //#include <lp_solver_wrapper_2.h>
marci@1017: #include <min_cost_gen_flow.h>
marci@764: 
marci@764: // Use a DIMACS max flow file as stdin.
marci@764: // max_flow_demo < dimacs_max_flow_file
marci@764: 
marci@1015: using namespace lemon;
marci@1015: 
marci@764: int main(int, char **) {
marci@764: 
marci@1014:   typedef ListGraph MutableGraph;
marci@1025:   typedef ListGraph Graph;
marci@764:   typedef Graph::Node Node;
marci@1015:   typedef Graph::Edge Edge;
marci@764:   typedef Graph::EdgeIt EdgeIt;
marci@764: 
marci@764:   Graph g;
marci@764: 
marci@764:   Node s, t;
marci@764:   Graph::EdgeMap<int> cap(g);
marci@764:   //readDimacsMaxFlow(std::cin, g, s, t, cap);
marci@764:   readDimacs(std::cin, g, cap, s, t);
marci@764:   Timer ts;
marci@764:   Graph::EdgeMap<int> flow(g); //0 flow
marci@1014:   Preflow<Graph, int, Graph::EdgeMap<int>, Graph::EdgeMap<int> > 
marci@764:     max_flow_test(g, s, t, cap, flow);
marci@764:   AugmentingFlow<Graph, int, Graph::EdgeMap<int>, Graph::EdgeMap<int> > 
marci@764:     augmenting_flow_test(g, s, t, cap, flow);
marci@764:   
marci@764:   Graph::NodeMap<bool> cut(g);
marci@764: 
marci@764:   {
marci@764:     std::cout << "preflow ..." << std::endl;
marci@764:     ts.reset();
marci@764:     max_flow_test.run();
marci@764:     std::cout << "elapsed time: " << ts << std::endl;
marci@764:     std::cout << "flow value: "<< max_flow_test.flowValue() << std::endl;
marci@1014:     max_flow_test.minCut(cut);
marci@764: 
marci@1015:     for (EdgeIt e(g); e!=INVALID; ++e) {
alpar@986:       if (cut[g.source(e)] && !cut[g.target(e)] && !flow[e]==cap[e]) 
marci@764: 	std::cout << "Slackness does not hold!" << std::endl;
alpar@986:       if (!cut[g.source(e)] && cut[g.target(e)] && flow[e]>0) 
marci@764: 	std::cout << "Slackness does not hold!" << std::endl;
marci@764:     }
marci@764:   }
marci@764: 
marci@764: //   {
marci@764: //     std::cout << "preflow ..." << std::endl;
marci@764: //     FOR_EACH_LOC(Graph::EdgeIt, e, g) flow.set(e, 0);
marci@764: //     ts.reset();
marci@1014: //     max_flow_test.preflow(Preflow<Graph, int, Graph::EdgeMap<int>, Graph::EdgeMap<int> >::GEN_FLOW);
marci@764: //     std::cout << "elapsed time: " << ts << std::endl;
marci@764: //     std::cout << "flow value: "<< max_flow_test.flowValue() << std::endl;
marci@764: 
marci@764: //     FOR_EACH_LOC(Graph::EdgeIt, e, g) {
alpar@986: //       if (cut[g.source(e)] && !cut[g.target(e)] && !flow[e]==cap[e]) 
marci@764: // 	std::cout << "Slackness does not hold!" << std::endl;
alpar@986: //       if (!cut[g.source(e)] && cut[g.target(e)] && flow[e]>0) 
marci@764: // 	std::cout << "Slackness does not hold!" << std::endl;
marci@764: //     }
marci@764: //   }
marci@764: 
marci@764: //   {
marci@764: //     std::cout << "wrapped preflow ..." << std::endl;
marci@764: //     FOR_EACH_LOC(Graph::EdgeIt, e, g) flow.set(e, 0);
marci@764: //     ts.reset();
marci@764: //     pre_flow_res.run();
marci@764: //     std::cout << "elapsed time: " << ts << std::endl;
marci@764: //     std::cout << "flow value: "<< pre_flow_test.flowValue() << std::endl;
marci@764: //   }
marci@764: 
marci@764:   {
marci@764:     std::cout << "physical blocking flow augmentation ..." << std::endl;
marci@1015:     for (EdgeIt e(g); e!=INVALID; ++e) flow.set(e, 0);
marci@764:     ts.reset();
marci@764:     int i=0;
marci@764:     while (augmenting_flow_test.augmentOnBlockingFlow<MutableGraph>()) { ++i; }
marci@764:     std::cout << "elapsed time: " << ts << std::endl;
marci@764:     std::cout << "number of augmentation phases: " << i << std::endl; 
marci@764:     std::cout << "flow value: "<< augmenting_flow_test.flowValue() << std::endl;
marci@764: 
marci@1015:     for (EdgeIt e(g); e!=INVALID; ++e) {
alpar@986:       if (cut[g.source(e)] && !cut[g.target(e)] && !flow[e]==cap[e]) 
marci@764: 	std::cout << "Slackness does not hold!" << std::endl;
alpar@986:       if (!cut[g.source(e)] && cut[g.target(e)] && flow[e]>0) 
marci@764: 	std::cout << "Slackness does not hold!" << std::endl;
marci@764:     }
marci@764:   }
marci@764: 
marci@764: //   {
marci@764: //     std::cout << "faster physical blocking flow augmentation ..." << std::endl;
marci@764: //     FOR_EACH_LOC(Graph::EdgeIt, e, g) flow.set(e, 0);
marci@764: //     ts.reset();
marci@764: //     int i=0;
marci@764: //     while (max_flow_test.augmentOnBlockingFlow1<MutableGraph>()) { ++i; }
marci@764: //     std::cout << "elapsed time: " << ts << std::endl;
marci@764: //     std::cout << "number of augmentation phases: " << i << std::endl; 
marci@764: //     std::cout << "flow value: "<< max_flow_test.flowValue() << std::endl;
marci@764: //   }
marci@764: 
marci@764:   {
marci@764:     std::cout << "on-the-fly blocking flow augmentation ..." << std::endl;
marci@1015:     for (EdgeIt e(g); e!=INVALID; ++e) flow.set(e, 0);
marci@764:     ts.reset();
marci@764:     int i=0;
marci@764:     while (augmenting_flow_test.augmentOnBlockingFlow2()) { ++i; }
marci@764:     std::cout << "elapsed time: " << ts << std::endl;
marci@764:     std::cout << "number of augmentation phases: " << i << std::endl; 
marci@764:     std::cout << "flow value: "<< augmenting_flow_test.flowValue() << std::endl;
marci@764: 
marci@1015:     for (EdgeIt e(g); e!=INVALID; ++e) {
alpar@986:       if (cut[g.source(e)] && !cut[g.target(e)] && !flow[e]==cap[e]) 
marci@764: 	std::cout << "Slackness does not hold!" << std::endl;
alpar@986:       if (!cut[g.source(e)] && cut[g.target(e)] && flow[e]>0) 
marci@764: 	std::cout << "Slackness does not hold!" << std::endl;
marci@764:     }
marci@764:   }
marci@764: 
marci@764: //   {
marci@764: //     std::cout << "on-the-fly shortest path augmentation ..." << std::endl;
marci@764: //     FOR_EACH_LOC(Graph::EdgeIt, e, g) flow.set(e, 0);
marci@764: //     ts.reset();
marci@764: //     int i=0;
marci@764: //     while (augmenting_flow_test.augmentOnShortestPath()) { ++i; }
marci@764: //     std::cout << "elapsed time: " << ts << std::endl;
marci@764: //     std::cout << "number of augmentation phases: " << i << std::endl; 
marci@764: //     std::cout << "flow value: "<< augmenting_flow_test.flowValue() << std::endl;
marci@764: 
marci@764: //     FOR_EACH_LOC(Graph::EdgeIt, e, g) {
alpar@986: //       if (cut[g.source(e)] && !cut[g.target(e)] && !flow[e]==cap[e]) 
marci@764: // 	std::cout << "Slackness does not hold!" << std::endl;
alpar@986: //       if (!cut[g.source(e)] && cut[g.target(e)] && flow[e]>0) 
marci@764: // 	std::cout << "Slackness does not hold!" << std::endl;
marci@764: //     }
marci@764: //   }
marci@764: 
marci@764: //   {
marci@764: //     std::cout << "on-the-fly shortest path augmentation ..." << std::endl;
marci@764: //     FOR_EACH_LOC(Graph::EdgeIt, e, g) flow.set(e, 0);
marci@764: //     ts.reset();
marci@764: //     int i=0;
marci@764: //     while (augmenting_flow_test.augmentOnShortestPath2()) { ++i; }
marci@764: //     std::cout << "elapsed time: " << ts << std::endl;
marci@764: //     std::cout << "number of augmentation phases: " << i << std::endl; 
marci@764: //     std::cout << "flow value: "<< augmenting_flow_test.flowValue() << std::endl;
marci@764: 
marci@764: //     FOR_EACH_LOC(Graph::EdgeIt, e, g) {
alpar@986: //       if (cut[g.source(e)] && !cut[g.target(e)] && !flow[e]==cap[e]) 
marci@764: // 	std::cout << "Slackness does not hold!" << std::endl;
alpar@986: //       if (!cut[g.source(e)] && cut[g.target(e)] && flow[e]>0) 
marci@764: // 	std::cout << "Slackness does not hold!" << std::endl;
marci@764: //     }
marci@764: //   }
marci@764: 
marci@764:   ts.reset();
marci@1015: 
marci@1015:   Edge e=g.addEdge(t, s);
marci@1015:   Graph::EdgeMap<int> cost(g, 0);
marci@1015:   cost.set(e, -1);
marci@1015:   cap.set(e, 10000);
marci@1015:   typedef ConstMap<Node, int> Excess;
marci@1015:   Excess excess(0);
marci@1015:   typedef ConstMap<Edge, int> LCap;
marci@1015:   LCap lcap(0);
marci@1015: 
marci@1015:   MinCostGenFlow<Graph, int, Excess, LCap> 
marci@1015:     min_cost(g, excess, lcap, cap, flow, cost); 
marci@1025:   min_cost.feasible();
marci@1031:   min_cost.runByLP();
marci@1015: 
marci@764:   std::cout << "elapsed time: " << ts << std::endl;
marci@1015:   std::cout << "flow value: "<< flow[e] << std::endl;
marci@764: }