HDU 3549 Flow Problem(最大流入门)

来源:互联网 发布:网络上长者是谁 编辑:程序博客网 时间:2024/06/05 06:24

题意:给你一个N个顶点M条边的有向图,要你求1号点到N号点的最大流.

思路:模板题...试了一下刘汝佳的Edmonds_Karp和Dinic模板,如果要处理无向图,那么对于无向图的每条边,你需要再图上添加两个方向的边各一条且流量费用相同。


/*EK算法 234MS*/#include <cstdio>#include <queue>#include <cstring>#include <iostream>#include <cstdlib>#include <algorithm>#include <vector>#include <map>#include <string>#include <set>#include <ctime>#include <cmath>#include <cctype>using namespace std;#define maxn 20#define INF 1<<20#define LL long longint cas=1,T;struct Edge{int from,to,cap,flow;Edge(int u,int v,int c,int f):from(u),to(v),cap(c),flow(f){}};int n,m;struct EdmondsKarp{//int n,m;vector<Edge>edges;        //边数的两倍vector<int> G[maxn];      //邻接表,G[i][j]表示结点i的第j条边在e数组中的序号int a[maxn];              //当起点到i的可改进量int p[maxn];              //最短路上p的入弧编号void init(){   for (int i=0;i<=n;i++)   G[i].clear();   edges.clear();}void AddEdge(int from,int to,int cap){edges.push_back(Edge(from,to,cap,0));edges.push_back(Edge(to,from,0,0));        //反向弧int mm=edges.size();G[from].push_back(mm-2);G[to].push_back(mm-1);}    int Maxflow(int s,int t){int flow=0;for (;;){memset(a,0,sizeof(a));queue<int>q;q.push(s);a[s]=INF;while (!q.empty()){int x = q.front();q.pop();for (int i = 0;i<G[x].size();i++){Edge &e = edges[G[x][i]];if (!a[e.to] && e.cap>e.flow){p[e.to]=G[x][i];a[e.to]=min(a[x],e.cap-e.flow);q.push(e.to);}}if (a[t])break;}if (!a[t])break;for (int u=t;u!=s;u=edges[p[u]].from){edges[p[u]].flow+=a[t];edges[p[u]^1].flow-=a[t];}flow+=a[t];}return flow;}};int main(){//freopen("in","r",stdin);scanf("%d",&T);while (T--){EdmondsKarp ek;scanf("%d%d",&n,&m);ek.init();        for (int i = 0;i<m;i++){int u,v,c;scanf("%d%d%d",&u,&v,&c);ek.AddEdge(u,v,c);}printf("Case %d: %d\n",cas++,ek.Maxflow(1,n));}//printf("time=%.3lf",(double)clock()/CLOCKS_PER_SEC);return 0;}



/*Dinic  170MS*/#include <cstdio>#include <queue>#include <cstring>#include <iostream>#include <cstdlib>#include <algorithm>#include <vector>#include <map>#include <string>#include <set>#include <ctime>#include <cmath>#include <cctype>using namespace std;#define maxn 20#define INF 1e9#define LL long longint cas=1,T;struct Edge{int from,to,cap,flow;Edge(int u,int v,int c,int f):from(u),to(v),cap(c),flow(f){}};int n,m;struct Dinic{//int n,m;    int s,t;vector<Edge>edges;        //边数的两倍vector<int> G[maxn];      //邻接表,G[i][j]表示结点i的第j条边在e数组中的序号bool vis[maxn];           //BFS使用int d[maxn];              //从起点到i的距离int cur[maxn];            //当前弧下标void init(){   for (int i=0;i<=n;i++)   G[i].clear();   edges.clear();}void AddEdge(int from,int to,int cap){edges.push_back(Edge(from,to,cap,0));edges.push_back(Edge(to,from,0,0));        //反向弧int mm=edges.size();G[from].push_back(mm-2);G[to].push_back(mm-1);}bool BFS(){memset(vis,0,sizeof(vis));queue<int>q;q.push(s);d[s]=0;vis[s]=1;while (!q.empty()){int x = q.front();q.pop();for (int i = 0;i<G[x].size();i++){Edge &e = edges[G[x][i]];if (!vis[e.to] && e.cap > e.flow){vis[e.to]=1;d[e.to] = d[x]+1;q.push(e.to);}}}return vis[t];}int DFS(int x,int a){if (x==t || a==0)return a;int flow = 0,f;for(int &i=cur[x];i<G[x].size();i++){Edge &e = edges[G[x][i]];if (d[x]+1 == d[e.to] && (f=DFS(e.to,min(a,e.cap-e.flow)))>0){e.flow+=f;edges[G[x][i]^1].flow-=f;flow+=f;a-=f;if (a==0)break;}}return flow;}int Maxflow(int s,int t){this->s=s;this->t=t;int flow = 0;while (BFS()){memset(cur,0,sizeof(cur));flow+=DFS(s,INF);}return flow;}};int main(){//freopen("in","r",stdin);scanf("%d",&T);while (T--){Dinic dc;scanf("%d%d",&n,&m);dc.init();        for (int i = 0;i<m;i++){int u,v,c;scanf("%d%d%d",&u,&v,&c);dc.AddEdge(u,v,c);}printf("Case %d: %d\n",cas++,dc.Maxflow(1,n));}//printf("time=%.3lf",(double)clock()/CLOCKS_PER_SEC);return 0;}


Description

Network flow is a well-known difficult problem for ACMers. Given a graph, your task is to find out the maximum flow for the weighted directed graph.
 

Input

The first line of input contains an integer T, denoting the number of test cases. 
For each test case, the first line contains two integers N and M, denoting the number of vertexes and edges in the graph. (2 <= N <= 15, 0 <= M <= 1000) 
Next M lines, each line contains three integers X, Y and C, there is an edge from X to Y and the capacity of it is C. (1 <= X, Y <= N, 1 <= C <= 1000)
 

Output

For each test cases, you should output the maximum flow from source 1 to sink N.
 

Sample Input

23 21 2 12 3 13 31 2 12 3 11 3 1
 

Sample Output

Case 1: 1Case 2: 2
 


0 0
原创粉丝点击