题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1532
Drainage Ditches
Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Others)
Total Submission(s): 18864 Accepted Submission(s): 8980
Farmer John knows not only how many gallons of water each ditch can transport per minute but also the exact layout of the ditches, which feed out of the pond and into each other and stream in a potentially complex network.
Given all this information, determine the maximum rate at which water can be transported out of the pond and into the stream. For any given ditch, water flows in only one direction, but there might be a way that water can flow in a circle.
题解:
纯最大流。
代码如下:
1 #include <iostream> 2 #include <cstdio> 3 #include <cstring> 4 #include <algorithm> 5 #include <vector> 6 #include <cmath> 7 #include <queue> 8 #include <stack> 9 #include <map> 10 #include <string> 11 #include <set> 12 #define ms(a,b) memset((a),(b),sizeof((a))) 13 using namespace std; 14 typedef long long LL; 15 const int INF = 2e9; 16 const LL LNF = 9e18; 17 const int mod = 1e9+7; 18 const int MAXN = 500+10; 19 20 struct Edge 21 { 22 int to, next, cap, flow; 23 }edge[MAXN*MAXN]; 24 int tot, head[MAXN]; 25 26 int gap[MAXN], dep[MAXN], pre[MAXN], cur[MAXN]; 27 28 void add(int u, int v, int w) 29 { 30 edge[tot].to = v; edge[tot].cap = w; edge[tot].flow = 0; 31 edge[tot].next = head[u]; head[u] = tot++; 32 33 edge[tot].to = u; edge[tot].cap = 0; edge[tot].flow = 0; 34 edge[tot].next = head[v]; head[v] = tot++; 35 } 36 37 int sap(int start, int end, int n) 38 { 39 memset(gap,0,sizeof(gap)); 40 memset(dep,0,sizeof(dep)); 41 memcpy(cur,head,sizeof(head)); 42 int u = start; 43 pre[u] = -1; 44 gap[0] = n; 45 int maxflow = 0; 46 while(dep[start]<n) 47 { 48 bool flag = false; 49 for(int i = cur[u]; i!=-1; i=edge[i].next) 50 { 51 int v = edge[i].to; 52 if(edge[i].cap-edge[i].flow && dep[v]+1==dep[u]) 53 { 54 flag = true; 55 cur[u] = pre[v] = i; 56 u = v; 57 break; 58 } 59 } 60 61 if(flag) 62 { 63 if(u==end) 64 { 65 int minn = INF; 66 for(int i = pre[u]; i!=-1; i=pre[edge[i^1].to]) 67 if(minn>edge[i].cap-edge[i].flow) 68 minn = edge[i].cap-edge[i].flow; 69 for(int i = pre[u]; i!=-1; i=pre[edge[i^1].to]) 70 { 71 edge[i].flow += minn; 72 edge[i^1].flow -= minn; 73 } 74 u = start; 75 maxflow += minn; 76 } 77 } 78 79 else 80 { 81 int minn = n; 82 for(int i = head[u]; i!=-1; i=edge[i].next) 83 if(edge[i].cap-edge[i].flow && dep[edge[i].to]<minn) 84 { 85 minn = dep[edge[i].to]; 86 cur[u] = i; 87 } 88 gap[dep[u]]--; 89 if(gap[dep[u]]==0) break; 90 dep[u] = minn+1; 91 gap[dep[u]]++; 92 if(u!=start) u = edge[pre[u]^1].to; 93 } 94 } 95 return maxflow; 96 } 97 98 int main() 99 { 100 int n, m; 101 while(scanf("%d%d",&m,&n)!=EOF) 102 { 103 tot = 0; 104 memset(head,-1,sizeof(head)); 105 for(int i = 1; i<=m; i++) 106 { 107 int u, v, c; 108 scanf("%d%d%d",&u,&v,&c); 109 add(u, v, c); 110 } 111 cout<< sap(1, n, n) <<endl; 112 } 113 }