POJ 1459 最大流

//11166005	c00h00g	1459	Accepted	688K	579MS	G++	1585B	2013-01-08 22:10:35
//第一道网络流
//需要添加源点s和汇点t,power station上的最大发电量转化为源点到该发电站边的容量,同理consumer到t的边的容量为consumer的最大耗电量
//这一题读入是难点,如果使用c++读入比较简单,使用c读入的话需要注意前面还有一个空格 
//使用的是算法竞赛入门经典上的模板 
#include<stdio.h>
#include<stdlib.h>
#include<queue>
#include<string.h>
using namespace std; 
#define INF 0x7FFFFFFF
//父节点,初始化为-1 
int p[105];
//容量 
int cap[105][105]; 
//流 
int flow[105][105]; 
//用来记录最小的权值 
int a[105];

int main(){
    int n,np,nc,m,from,to,w,i,j,s,t;
    while(scanf("%d%d%d%d",&n,&np,&nc,&m)!=EOF){
        memset(p,-1,sizeof(p));
        memset(cap,0,sizeof(cap));
        memset(flow,0,sizeof(flow)); 
        //建图 
        for(i=0;i<m;i++){
            scanf(" (%d,%d)%d",&from,&to,&w);
            cap[++from][++to]=w;
        }
        for(i=0;i<np;i++){
            scanf(" (%d)%d",&to,&w);
            cap[0][++to]=w;
        }
        for(i=0;i<nc;i++){
            scanf(" (%d)%d",&from,&w);
            cap[++from][n+1]=w;
        }
        //求解 
        queue<int> q;
        int res=0;
        s=0,t=n+1;
        for(;;){
            memset(a,0,sizeof(a));
            a[s]=INF;
            q.push(s);
            while(!q.empty()){
                int u=q.front();q.pop();
                for(int v=0;v<=n+1;v++)
                    if(!a[v]&&cap[u][v]>flow[u][v]){
                        p[v]=u;q.push(v);
                        a[v]=((a[u]<(cap[u][v]-flow[u][v]))?a[u]:(cap[u][v]-flow[u][v]));
                    }
            }
            if(a[t]==0)
                break;
            for(int u=t;u!=s;u=p[u]){
                flow[p[u]][u]+=a[t];
                flow[u][p[u]]-=a[t];
            }
            res+=a[t];
        }
        printf("%d\n",res);
    }
    return 0;
}

你可能感兴趣的:(POJ 1459 最大流)