HDU 3917 最大权闭合图 求最小割

具体参考http://blog.csdn.net/power721/article/details/6665750

TODO

//#pragma comment(linker, "/STACK:16777216") //for c++ Compiler
#include <stdio.h>
#include <iostream>
#include <cstring>
#include <cmath>
#include <stack>
#include <queue>
#include <vector>
#include <algorithm>
#define ll long long
#define Max(a,b) (((a) > (b)) ? (a) : (b))
#define Min(a,b) (((a) < (b)) ? (a) : (b))
#define Abs(x) (((x) > 0) ? (x) : (-(x)))
#define N 8005
#define M 1000005
#define min(a,b) ((a)<(b)?(a):(b))
using namespace std;

const int inf = 0x3f3f3f3f;

int n,m,s,t,num;
int adj[N],dis[N],q[N];
vector<int> st[1005],ed[1005];
struct edge{
    int v,w,pre;
}e[M];
void insert(int u,int v,int w){
    e[num]=(edge){v,w,adj[u]};
    adj[u]=num++;
    e[num]=(edge){u,0,adj[v]};
    adj[v]=num++;
}

int bfs(){
    int i,x,v,head=0,tail=0;
    memset(dis,0,sizeof(dis));
    dis[s]=1;
    q[tail++]=s;
    while(head<tail){
        x=q[head++];
        for(i=adj[x];~i;i=e[i].pre)
            if(e[i].w&&!dis[v=e[i].v]){
                dis[v]=dis[x]+1;
                if(v==t)
                    return 1;
                q[tail++]=v;
            }
    }
    return 0;
}
int dfs(int x,int limit){
    if(x==t)
        return limit;
    int i,v,tmp,cost=0;
    for(i=adj[x];~i&&cost<limit;i=e[i].pre)
        if(e[i].w&&dis[x]==dis[v=e[i].v]-1){
            tmp=dfs(v,min(limit-cost,e[i].w));
            if(tmp){
                e[i].w-=tmp;
                e[i^1].w+=tmp;
                cost+=tmp;
            }
            else
                dis[v]=-1;
        }
    return cost;
}
int Dinic(){
    int ans=0;
    while(bfs())
        ans+=dfs(s,inf);
    return    ans;
}

int main(){
    while(scanf("%d%d",&n,&m),n+m){
        int i,j,k,u,v,c,w[5005]={0},sum=0;
        num=0;
        memset(adj,-1,sizeof(adj));
        s=0;
        t=1;
        for(i=1;i<=n;i++){
            st[i].clear();
            ed[i].clear();
        }
        for(i=1;i<=m;i++){
            scanf("%d",w+i);
            sum+=w[i];
            insert(i+1,t,w[i]);
        }
        scanf("%d",&k);
        for(i=1;i<=k;i++){
            scanf("%d%d%d%d",&u,&v,&c,&w[0]);
            insert(s,i+m+1,w[0]);
            insert(i+m+1,c+1,inf);
            st[u].push_back(c);
            ed[v].push_back(c);
        }
        for(i=1;i<=n;i++){
            for(j=0;j<ed[i].size();j++){
                for(k=0;k<st[i].size();k++){
                    insert(st[i][k]+1,ed[i][j]+1,inf);          //建无穷边
                    //printf("%d %d %d
",i,ed[i][j],st[i][k]);
                }
            }
        }
        printf("%d
",sum-Dinic());
    }
}
原文地址:https://www.cnblogs.com/wushuaiyi/p/4234987.html