Advertisement
RaFiN_

max flow

Apr 2nd, 2019
199
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 4.60 KB | None | 0 0
  1. /// ********** FASTER one *******************///
  2. namespace mf
  3. {
  4.     const int MAXN = 10004;
  5.     struct edge {
  6.         int a, b, cap, flow ;
  7.         edge(int _a,int _b,int _c,int _d) {
  8.             a=_a,b=_b,cap=_c,flow=_d;
  9.         }
  10.     } ;
  11.  
  12.     int INF=1500000001;
  13.  
  14.     int n, s, t, d [ MAXN*2 ] , ptr [ MAXN*2 ] , q [ MAXN*2*10 ] ;
  15.     vector < edge > e ;
  16.     vector < int > g [ MAXN * 2 ] ;
  17.  
  18.     void addEdge ( int a, int b, int cap ,int cap2=0) {
  19.         edge e1 =edge( a, b, cap, 0 ) ; /// forward cap
  20.         edge e2 =edge( b, a, cap2 , 0 ) ; /// backward cap change here if needed
  21.         g [ a ] . push_back ( ( int ) e. size ( ) ) ;
  22.         e. push_back ( e1 ) ;
  23.         g [ b ] . push_back ( ( int ) e. size ( ) ) ;
  24.         e. push_back ( e2 ) ;
  25.     }
  26.  
  27.     bool bfs ( ) {
  28.         int qh = 0 , qt = 0 ;
  29.         q [ qt ++ ] = s ;
  30.         memset ( d, -1 , sizeof d ) ;
  31.         d [ s ] = 0 ;
  32.         while ( qh < qt && d [ t ] == - 1 ) {
  33.             int v = q [ qh ++ ] ;
  34.             for ( size_t i = 0 ; i < g [ v ] . size ( ) ; ++ i ) {
  35.                 int id = g [ v ] [ i ] ,
  36.                     to = e [ id ] . b ;
  37.                 if ( d [ to ] == - 1 && e [ id ] . flow < e [ id ] . cap ) {
  38.                     q [ qt ++ ] = to ;
  39.                     d [ to ] = d [ v ] + 1 ;
  40.                 }
  41.             }
  42.         }
  43.         return d [ t ] != -1;
  44.     }
  45.  
  46.     int dfs ( int v, int flow ) {
  47.         if ( ! flow )  return 0 ;
  48.         if ( v == t )  return flow ;
  49.         for ( ; ptr [ v ] < ( int ) g [ v ] . size ( ) ; ++ ptr [ v ] ) {
  50.             int id = g [ v ] [ ptr [ v ] ] ,
  51.                 to = e [ id ] . b ;
  52.             if ( d [ to ] != d [ v ] + 1 )  continue ;
  53.             int pushed = dfs ( to, min ( flow, e [ id ] . cap - e [ id ] . flow ) ) ;
  54.             if ( pushed ) {
  55.                 e [ id ] . flow += pushed ;
  56.                 e [ id ^ 1 ] . flow -= pushed ;
  57.                 return pushed ;
  58.             }
  59.         }
  60.         return 0 ;
  61.     }
  62.  
  63.     ll dinic ( ) {
  64.         ll flow = 0 ;
  65.         for ( ;; ) {
  66.             if ( !bfs () )  break ;
  67.             memset ( ptr, 0 , sizeof ptr ) ;
  68.             while ( int pushed = dfs ( s, INF ) ) {
  69.                 flow += (ll)pushed ;
  70.                 if(pushed == 0)break;
  71.             }
  72.         }
  73.         return flow ;
  74.     }
  75.  
  76.     void init(int src, int dest , int nodes){
  77.         e.clear();
  78.         FOR(i,0,n+n) g[i].clear();
  79.         n = nodes; s = src; t = dest;
  80.     }
  81. };
  82.  
  83.  
  84.  
  85.  
  86. /**
  87. max flow (dinitz algorithm)
  88. works on undirected graph
  89. can have loops, multiple edges, cycles
  90. **/
  91.  
  92.  
  93. /**
  94. *********   MUST be 1 indexed
  95. *********   0 can not be a node
  96. **/
  97. namespace mf
  98. {
  99.     int src, snk, nNode, nEdge;
  100.     const int MAXN = 104;
  101.     const int MAXE = 20004; /// MAXE = twice the number of edges
  102.     int INF=1500000001;
  103.     int Q[MAXN], fin[MAXN], pro[MAXN], dist[MAXN];
  104.     int flow[MAXE], cap[MAXE], nextt[MAXE], to[MAXE];
  105.  
  106.     inline void init(int _src, int _snk, int _n) {
  107.         src = _src, snk = _snk, nNode = _n, nEdge = 0;
  108.         SET(fin);
  109.     }
  110.  
  111.     /// for directed graph _cap2 = 0
  112.     inline void addEdge(int u, int v, int _cap, int _cap2) {
  113.         to[nEdge] = v, cap[nEdge] = _cap, flow[nEdge] = 0;
  114.         nextt[nEdge] = fin[u], fin[u] = nEdge++;
  115.         to[nEdge] = u, cap[nEdge] = _cap2, flow[nEdge] = 0;
  116.         nextt[nEdge] = fin[v], fin[v] = nEdge++;
  117.     }
  118.  
  119.     bool bfs() {
  120.         int st, en, i, u, v;
  121.         SET(dist);
  122.         dist[src] = st = en = 0;
  123.         Q[en++] = src;
  124.         while(st < en) {
  125.             u = Q[st++];
  126.             for(i=fin[u]; i>=0; i=nextt[i]) {
  127.                 v = to[i];
  128.                 if(flow[i] < cap[i] && dist[v]==-1) {
  129.                     dist[v] = dist[u]+1;
  130.                     Q[en++] = v;
  131.                 }
  132.             }
  133.         }
  134.         return dist[snk]!=-1;
  135.     }
  136.  
  137.     int dfs(int u, int fl) {
  138.         if(u==snk) return fl;
  139.         for(int &e=pro[u], v, df; e>=0; e=nextt[e]) {
  140.             v = to[e];
  141.             if(flow[e] < cap[e] && dist[v]==dist[u]+1) {
  142.                 df = dfs(v, min(cap[e]-flow[e], fl));
  143.                 if(df>0) {
  144.                     flow[e] += df;
  145.                     flow[e^1] -= df;
  146.                     return df;
  147.                 }
  148.             }
  149.         }
  150.         return 0;
  151.     }
  152.  
  153.     ll dinitz() {
  154.         ll ret = 0;
  155.         ll df;
  156.         for(int i=1; i<=nNode; i++) pro[i] = fin[i];
  157.         while(bfs()) {
  158.  
  159.             while(true) {
  160.                 df = dfs(src, INF);
  161.                 if(df) ret += df;
  162.                 else break;
  163.             }
  164.         }
  165.         return ret;
  166.     }
  167. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement