【網路流之最大流】POJ1273-Drainage Ditche【模板題】
阿新 • • 發佈:2019-01-05
這是一道網路流的入門題,用來理解最大流很好。
#include<iostream> #include<string> #include<cstdio> #include<cstring> #include<map> #include<queue> #include<cmath> #include<stack> #include<set> #include<vector> #include<algorithm> #define LL long long #define inf 1<<29 #define s(a) scanf("%d",&a) #define CL(a,b) memset(a,b,sizeof(a)) using namespace std; const int N=205; int n,m,u,v,cost; int Map[N][N],path[N],flow[N]; int start,endd; queue<int>q; int bfs() { while(!q.empty()) q.pop(); CL(path,-1); path[start]=0,flow[start]=inf; // 起始容量為inf; q.push(start); while(!q.empty()){ int t=q.front(); q.pop(); if(t==endd) break; for(int i=1;i<=m;i++){ // 遍歷可走路徑; if(i!=start&&path[i]==-1&&Map[t][i]){ // 符合這三種情況表示該路徑可走; flow[i]=flow[t]<Map[t][i]?flow[t]:Map[t][i]; q.push(i); path[i]=t; } } } if(path[endd]==-1) return -1; // 說明沒有找到可走路徑,返回-1; return flow[endd]; // 找到一條路徑之後的增流量; } int Edmonds_Karp() { int max_flow=0,step,now,pre; while((step=bfs())!=-1){ // 找不到路徑之後便退出; max_flow+=step; // 累加流量; now=endd; while(now!=start){ // 將找到的路徑進行反向處理,並更新實際容量; pre=path[now]; Map[pre][now]-=step; // 更新正向邊的實際容量; Map[now][pre]+=step; // 新增反向邊; now=pre; } } return max_flow; } int main() { while(~scanf("%d%d",&n,&m)){ CL(Map,0); for(int i=0;i<n;i++){ scanf("%d%d%d",&u,&v,&cost); Map[u][v]+=cost; // 為防止一條邊不止一次輸入; } start=1,endd=m; printf("%d\n",Edmonds_Karp()); } return 0; }