图论算法-网络最大流【EK;Dinic】

来源:互联网 发布:远程oracle数据库拷贝 编辑:程序博客网 时间:2024/06/07 06:03

图论算法-网络最大流模板【EK;Dinic】


EK模板

每次找出增广后残量网络中的最小残量增加流量

const int inf=1e9;int n,m,s,t;struct node{int v,cap;};vector<node> map[100010];int flow[10010][10010];int a[100010];int pre[100010];int EK(){    int maxf;//记录最大流量    queue<int> q;    while(1)    {        memset(a,0,sizeof(a));        a[s]=inf;        q.push(s);        while(!q.empty())        {            int u=q.front();            q.pop();            for(int j=0;j<map[u].size();j++)            {                int v=map[u][j].v;                int cap=map[u][j].cap;                if(!a[v]&&cap>flow[u][v])                {                    pre[v]=u;                    q.push(v);                    a[v]=min(a[u],cap-flow[u][v]);                }            }        }        if(a[t]==0)        break;        for(int u=t;u!=s;u=pre[u])        {            flow[ pre[u] ][u]+=a[t];            flow[ u][ pre[u] ]-=a[t];        }        maxf+=a[t];    }    return  maxf;}int main(){    cin>>n>>m>>s>>t;    for(int i=1;i<=m;i++)    {        int u,v,dis;        cin>>u>>v>>dis;        map[u].push_back((node) {v,dis });        map[v].push_back((node) {u,0 });//**高亮**反向边一定要记得建    }    int ans=EK();    cout<<ans;    return 0;}

Dinic模板

构造层次+阻塞流增广

const int inf=1e9;int n,m;int s,t;int tot=1;struct node{int v,f,nxt;}E[1000010];int head[100010];int lev[100010];//记录层次void add(int u,int v,int cap){    E[++tot].v=v;    E[tot].nxt=head[u];    E[tot].f=cap;    head[u]=tot;}bool bfs(){    queue<int> q;    memset(lev,-1,sizeof(lev));    q.push(s);    lev[s]=0;    while(!q.empty())    {        int u=q.front();        q.pop();        for(int i=head[u];i;i=E[i].nxt)        {            int v=E[i].v;            if(lev[v]==-1&&E[i].f)            {                lev[v]=lev[u]+1;                if(v==t)                return true;                q.push(v);            }        }    }    return false;}int dfs(int u,int cap){    if(u==t)    return cap;    int flow=cap;    for(int i=head[u];i;i=E[i].nxt)    {        int v=E[i].v;        if(lev[v]==lev[u]+1&&flow&&E[i].f>0)        {            int f=dfs(v,min(flow,E[i].f));            flow-=f;            E[i].f-=f;            E[i^1].f+=f;        }    }    return cap-flow;}int dinic(){    int maxf=0;    while(bfs())//若s-t可达就不断构造层次图    maxf+=dfs(s,inf);//s-t可达,用阻塞流增广    return maxf;}int main(){    cin>>n>>m>>s>>t;    for(int i=1;i<=m;i++)    {        int u,v,w;        cin>>u>>v>>w;        add(u,v,w);        add(v,u,0);//**高亮**反向边一定要记得建    }    dinic();    cout<<maxf;    return 0;}
原创粉丝点击