码迷,mamicode.com
首页 > Web开发 > 详细

网络流模板 NetworkFlow

时间:2016-12-27 22:27:36      阅读:286      评论:0      收藏:0      [点我收藏+]

标签:with   dfs   problems   tail   ram   under   app   src   preview   

身边的小伙伴们都在愉快地刷网络流,我也来写一发模板好了。

 

Network Flow - Maximum Flow

Time Limit : 1 sec, Memory Limit : 65536 KB 
Japanese version is here

Maximum Flow

A flow network is a directed graph which has a 技术分享技术分享技术分享技术分享技术分享技术分享 and a 技术分享技术分享技术分享技术分享. In a flow network, each edge 技术分享技术分享技术分享技术分享技术分享has a capacity 技术分享技术分享技术分享技术分享技术分享技术分享. Each edge receives a flow, but the amount of flow on the edge can not exceed the corresponding capacity. Find the maximum flow from the 技术分享技术分享技术分享技术分享技术分享技术分享 to the 技术分享技术分享技术分享技术分享.

Input

A flow network is given in the following format.

技术分享技术分享技术分享技术分享技术分享技术分享
技术分享技术分享技术分享技术分享技术分享技术分享
技术分享技术分享技术分享技术分享技术分享技术分享
:
技术分享技术分享技术分享技术分享技术分享技术分享技术分享技术分享技术分享技术分享技术分享技术分享技术分享技术分享技术分享技术分享技术分享技术分享

技术分享技术分享技术分享技术分享技术分享技术分享 is the number of vertices and edges of the flow network respectively. The vertices in 技术分享 are named with the numbers 0, 1,..., 技术分享技术分享技术分享技术分享技术分享. The source is 0 and the sink is 技术分享技术分享技术分享技术分享技术分享.

技术分享技术分享技术分享技术分享技术分享技术分享 represent 技术分享-th edge of the flow network. A pair of 技术分享技术分享 and 技术分享技术分享 denotes that there is an edge from 技术分享技术分享to 技术分享技术分享 and 技术分享技术分享 is the capacity of 技术分享-th edge.

Output

Print the maximum flow.

Constraints

  • 技术分享技术分享技术分享技术分享技术分享技术分享技术分享技术分享技术分享
  • 技术分享技术分享技术分享技术分享技术分享技术分享技术分享技术分享技术分享技术分享
  • 技术分享技术分享技术分享技术分享技术分享技术分享技术分享技术分享技术分享技术分享

Sample Input 1

4 5
0 1 2
0 2 1
1 2 1
1 3 1
2 3 2

Sample Output 1

3

 

  1 #include <bits/stdc++.h>
  2 
  3 #define fread_siz 1024
  4 
  5 inline int get_c(void)
  6 {
  7     static char buf[fread_siz];
  8     static char *head = buf + fread_siz;
  9     static char *tail = buf + fread_siz;
 10 
 11     if (head == tail)
 12         fread(head = buf, 1, fread_siz, stdin);
 13 
 14     return *head++;
 15 }
 16 
 17 inline int get_i(void)
 18 {
 19     register int ret = 0;
 20     register int neg = false;
 21     register int bit = get_c();
 22 
 23     for (; bit < 48; bit = get_c())
 24         if (bit == -)neg ^= true;
 25 
 26     for (; bit > 47; bit = get_c())
 27         ret = ret * 10 + bit - 48;
 28 
 29     return neg ? -ret : ret;
 30 }
 31 
 32 template <class T>
 33 inline T min(T a, T b)
 34 {
 35     return a < b ? a : b;
 36 }
 37 
 38 const int inf = 2e9;
 39 const int maxn = 20005;
 40 
 41 int n, m;
 42 int s, t;
 43 
 44 int edges;
 45 int hd[maxn];
 46 int to[maxn];
 47 int nt[maxn];
 48 int fl[maxn];
 49 
 50 inline void add(int u, int v, int f)
 51 {
 52     nt[edges] = hd[u]; to[edges] = v; fl[edges] = f; hd[u] = edges++;
 53     nt[edges] = hd[v]; to[edges] = u; fl[edges] = 0; hd[v] = edges++;
 54 }
 55 
 56 int dep[maxn];
 57 
 58 inline bool bfs(void)
 59 {
 60     static int que[maxn];
 61     static int head, tail;
 62     
 63     memset(dep, 0, sizeof(dep));
 64     head = 0, tail = 0;
 65     que[tail++] = s;
 66     dep[s] = 1;
 67     
 68     while (head != tail)
 69     {
 70         int u = que[head++], v;
 71         for (int i = hd[u]; ~i; i = nt[i])
 72             if (!dep[v = to[i]] && fl[i])
 73                 dep[v] = dep[u] + 1, que[tail++] = v;
 74     }
 75     
 76     return dep[t];
 77 }
 78 
 79 inline int dfs(int u, int f)
 80 {
 81     if (u == t || !f)
 82         return f;
 83     
 84     int used = 0, flow, v;
 85     
 86     for (int i = hd[u]; ~i; i = nt[i])
 87         if (dep[v = to[i]] == dep[u] + 1 && fl[i])
 88         {
 89             flow = dfs(v, min(f - used, fl[i]));
 90             
 91             used += flow;
 92             fl[i] -= flow;
 93             fl[i^1] += flow;
 94             
 95             if (used == f)
 96                 return f;
 97         }
 98         
 99     if (!used)
100         dep[u] = 0;
101         
102     return used;
103 }
104 
105 inline int dinic(void)
106 {
107     int maxFlow = 0, newFlow;
108     
109     while (bfs())
110         while (newFlow = dfs(s, inf))
111             maxFlow += newFlow;
112             
113     return maxFlow;
114 }
115 
116 signed main(void)
117 {
118     n = get_i();
119     m = get_i();
120     
121     memset(hd, -1, sizeof(hd));
122     
123     for (int i = 1; i <= m; ++i)
124     {
125         int u = get_i();
126         int v = get_i();
127         int f = get_i();
128         add(u, v, f);
129     }
130     
131     s = 0, t = n - 1;
132     
133     printf("%d\n", dinic());
134 }

 

 

Network Flow - Minimum Cost Flow

Time Limit : 1 sec, Memory Limit : 65536 KB

最小費用流

各辺にコストが設定されたフローネットワークにおいて、始点 ss から終点 tt まで流用 FF のフローを流すための最小コストを求めてください。

フローネットワークの各辺 ee には容量 c(e)c(e) 及びコスト d(e)d(e) が設定されています。各辺 ee には容量 c(e)c(e)を超えない流量 f(e)f(e) のフローを流すことができます。始点 ss から終点 tt へ流量 FF のフローを流したときの、e(f(e)×d(e))∑e(f(e)×d(e)) の最小値を求めてください。

入力

フローネットワーク G(V,E)G(V,E) が以下の形式で与えられる。

|V||E|F|V||E|F
u0v0c0d0u0v0c0d0
u1v1c1d1u1v1c1d1
:
u|E|1v|E|1c|E|1d|E|1u|E|1v|E|−1c|E|−1d|E|−1

|V||V|, |E||E|, FF はそれぞれフローネットワーク GG の頂点の数、辺の数、流したい流量を示す。 GG の頂点にはそれぞれ 0,1,...,|V|10,1,...,|V|−1 の番号が付けられており、始点を 0、終点を |V|1|V|−1 とする。

uiui, vivi, cici, didi はフローネットワーク GG の ii 番目の辺を表し、頂点 uiui から頂点 vivi に向かって容量が cici でコストが didi の辺があることを表す。

出力

最小費用流を1行に出力する。ただし、始点 ss から終点 tt へ流量 FF のフローを流すことができない場合は -1 を1行に出力する。

制約

  • 2 ≤ |V||V| ≤ 100
  • 1 ≤ |E||E| ≤ 1000
  • 0 ≤ FF ≤ 1000
  • 0 ≤ cici, didi ≤ 1000
  • uiui ≠ vivi
  • 頂点 xx から頂点 yy に向かって辺がある場合、頂点 yy から頂点 xx に向かう辺(逆辺)はない。

入力例

4 5 2
0 1 2 1
0 2 1 2
1 2 1 1
1 3 1 3
2 3 2 1

出力例

6

 

  1 #include <bits/stdc++.h>
  2 
  3 #define fread_siz 1024
  4 
  5 inline int get_c(void)
  6 {
  7     static char buf[fread_siz];
  8     static char *head = buf + fread_siz;
  9     static char *tail = buf + fread_siz;
 10 
 11     if (head == tail)
 12         fread(head = buf, 1, fread_siz, stdin);
 13 
 14     return *head++;
 15 }
 16 
 17 inline int get_i(void)
 18 {
 19     register int ret = 0;
 20     register int neg = false;
 21     register int bit = get_c();
 22 
 23     for (; bit < 48; bit = get_c())
 24         if (bit == -)neg ^= true;
 25 
 26     for (; bit > 47; bit = get_c())
 27         ret = ret * 10 + bit - 48;
 28 
 29     return neg ? -ret : ret;
 30 }
 31 
 32 template <class T>
 33 inline T min(T a, T b)
 34 {
 35     return a < b ? a : b;
 36 }
 37 
 38 const int inf = 2e9;
 39 const int maxn = 2005;
 40 
 41 int n, m;
 42 int s, t;
 43 int flow;
 44 
 45 int edges;
 46 int hd[maxn];
 47 int nt[maxn];
 48 int to[maxn];
 49 int vl[maxn];
 50 int fl[maxn];
 51 
 52 inline void add(int u, int v, int f, int w)
 53 {
 54     nt[edges] = hd[u]; to[edges] = v; fl[edges] = f; vl[edges] = +w; hd[u] = edges++;
 55     nt[edges] = hd[v]; to[edges] = u; fl[edges] = 0; vl[edges] = -w; hd[v] = edges++;
 56 }
 57 
 58 int dis[maxn];
 59 int pre[maxn];
 60 
 61 inline bool spfa(void)
 62 {
 63     static int que[maxn];
 64     static int inq[maxn];
 65     static int head, tail;
 66     
 67     memset(dis, 0x3f, sizeof(dis));
 68     head = 0, tail = 0;
 69     que[tail++] = s;
 70     pre[s] = -1;
 71     inq[s] = 1;
 72     dis[s] = 0;
 73     
 74     while (head != tail)
 75     {
 76         int u = que[head++], v; inq[u] = 0;
 77         
 78         for (int i = hd[u]; ~i; i = nt[i])
 79             if (dis[v = to[i]] > dis[u] + vl[i] && fl[i])
 80             {
 81                 dis[v] = dis[u] + vl[i];
 82                 pre[v] = i ^ 1;
 83                 if (!inq[v])
 84                     inq[v] = 1, que[tail++] = v;
 85             }
 86     }
 87     
 88     return dis[t] < 0x3f3f3f3f;
 89 }
 90 
 91 inline int expend(void)
 92 {
 93     int newFlow = inf;
 94     
 95     for (int i = pre[t]; ~i; i = pre[to[i]])
 96         newFlow = min(newFlow, fl[i ^ 1]);
 97         
 98     for (int i = pre[t]; ~i; i = pre[to[i]])
 99         fl[i] += newFlow, fl[i^1] -= newFlow;
100         
101     return flow -= newFlow, newFlow * dis[t];
102 }
103 
104 inline int mcmf(void)
105 {
106     int ret = 0;
107     
108     while (spfa())
109         ret += expend();
110         
111     return flow ? -1 : ret;
112 }
113 
114 signed main(void)
115 {
116     n = get_i();
117     m = get_i();
118     
119     flow = get_i();
120     
121     memset(hd, -1, sizeof(hd));
122     
123     for (int i = 1; i <= m; ++i)
124     {
125         int u = get_i();
126         int v = get_i();
127         int f = get_i();
128         int w = get_i();
129         add(u, v, f, w);
130     }
131     
132     s = n, t = n - 1;
133     
134     add(s, 0, flow, 0);
135     
136     printf("%d\n", mcmf());
137 }

 

@Author: YouSiki

网络流模板 NetworkFlow

标签:with   dfs   problems   tail   ram   under   app   src   preview   

原文地址:http://www.cnblogs.com/yousiki/p/6227524.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!