hdoj 3549 Flow Problem---最大流---Edmond Karp算法

题目:http://acm.hdu.edu.cn/showproblem.php?pid=3549

典型的最大流,注意重边。

Edmond Karp算法:

反复寻找源点s到汇点t之间的增广路径,若有,找出增广路径上每一段[容量-流量]的最小值delta,若无,则结束。

在寻找增广路径时,可以用BFS来找,并且更新残留网络的值(涉及到反向边)。

而找到delta后,则使最大流值加上delta,更新为当前的最大流值。

#include <iostream>
#include <queue>
#include <algorithm>
#include <cstring>
#include <cstdlib>
using namespace std;
const int maxn=0xffffff;
int c[20][20];
int pre[20];
bool visit[20];
int n,m; //n vertexs,m edges
int min(int x,int y){
	return x<y?x:y;
}
bool bfs()
{
	memset(visit,0,sizeof(visit));
	queue<int> q;
	q.push(1);
	visit[1]=1;

	while(!q.empty())
	{
		int p=q.front();
		q.pop();
		for(int i=1;i<=n;i++)
		{
			if(!visit[i] && c[p][i]>0)
			{
				q.push(i);
				pre[i]=p;
				visit[i]=1;
				if(i==n)return 1;
			}
		}
	}
	return 0;
}
int ek()
{
	int maxflow=0;
	
	while(1)
	{
		int flag=bfs();
		if(!flag)break;
		int d=1<<30;
		int i=n;
		while(i!=1)
		{
			if(d>c[pre[i]][i])d=c[pre[i]][i];
			i=pre[i];
		}	
		i=n;
		while(i!=1)
		{
			c[pre[i]][i] -=d;
			c[i][pre[i]] +=d;
			i=pre[i];
		}
		maxflow+=d;
		//cout<<maxflow<<endl;
	}
	return maxflow;
}
int main()
{
	int t;
	cin>>t;
	for(int i=1;i<=t;i++)
	{
		cin>>n>>m;
		int x,y,z;
		memset(c,0,sizeof(c));
		for(int j=0;j<m;j++)
		{
			cin>>x>>y>>z;
			c[x][y]+=z;
		}
		cout<<"Case "<<i<<": ";
		cout<<ek()<<endl;
	}
	return 0;
}


你可能感兴趣的:(网络,最大流,EK算法)