当前位置: 代码迷 >> 综合 >> poj-1459-最大流-edmondskarp算法
  详细解决方案

poj-1459-最大流-edmondskarp算法

热度:48   发布时间:2023-12-19 11:31:18.0

搞了许久的最大流终于有眉头了,非常高兴~~

题意:有多个发电站,有多个用户,发电站和用户之间有多个中转站。

首先输入,总共点的个数,发电站的数目,用户数,边数。

对于每个边,输入两个点,为边的两点,然后输入此边允许的一个最大流量。

对于每个发电站,和每个用户来说,输入一个点,此点为发电站的后继点或者用户的前驱点,然后输入一个最大流量;

做法:

设立一个源点sp,一个节点fp。

sp指向所有的发电站。所有的用户指向fp。求sp到fp的最大流量。

对于edmondskarp算法,首先确定所有的点的最大流量和现有流量,然后每次加一个最小的边,直至无法继续加为止。

代码:

#include<iostream>
#include<Stdio.h>
#include<string.h>
#include<queue>
#define min(a,b) (a<b?a:b);
using namespace std;
struct list
{int flow;int cow;
}map[105][105];
int sp,fp;
int n,np,nc,m;
int maxflow;
int prv[105];//记录每次查找最小边的路径
int bfs(int st,int end)
{int i,v;int a[105];queue<int>q;memset(a,0,sizeof(a));memset(prv,-1,sizeof(prv));q.push(st);a[st]=10000;while(!q.empty()){v=q.front();q.pop();for(i=0;i<n;i++){if(!a[i]&&(map[v][i].cow>map[v][i].flow)){q.push(i);prv[i]=v;a[i]=min(a[v],map[v][i].cow-map[v][i].flow);//寻找该路径的最小边}}if(v==end)return a[end];}return 0;
}
void edmondskarp()
{int i,tmp;maxflow=0;while(bfs(sp,fp))//如果可以加边,就继续加{tmp=bfs(sp,fp);for(i=fp;i!=sp;i=prv[i]){map[prv[i]][i].flow+=tmp;map[i][prv[i]].flow-=tmp;}maxflow+=tmp;}
}
int main()
{int i,x,y,z;char ch;while(scanf("%d%d%d%d",&n,&np,&nc,&m)!=EOF){memset(map,0,sizeof(map));for(i=0;i<m;i++){cin>>ch>>x>>ch>>y>>ch>>z;map[x][y].cow=z;}sp=n;fp=n+1;n+=2;for(i=0;i<np;i++){cin>>ch>>x>>ch>>y;map[sp][x].cow=y;}for(i=0;i<nc;i++){cin>>ch>>x>>ch>>y;map[x][fp].cow=y;}edmondskarp();printf("%d\n",maxflow);}return 0;
}