zoukankan      html  css  js  c++  java
  • 【模板】最大流

    学会了 (Dinic) 算法。
    Dinic 算法的核心思想是多路增广。相比于 EK 算法,Dinic 算法利用了分层的思想,每次都寻找最短路径的增广路。时间复杂度为 (O(n^2m))

    代码如下

    #include <bits/stdc++.h>
    using namespace std;
    const int maxn=1e4+10;
    const int maxm=1e5+10;
    const int inf=0x3f3f3f3f;
    
    int n,m,s,t,maxflow,d[maxn];
    struct node{int nxt,to,w;}e[maxm<<1];
    int tot=1,head[maxn];
    inline void add_edge(int from,int to,int w){
    	e[++tot]=node{head[from],to,w},head[from]=tot;
    }
    
    bool bfs(){
    	queue<int> q;
    	memset(d,0,sizeof(d));
    	d[s]=1,q.push(s);
    	while(q.size()){
    		int u=q.front();q.pop();
    		for(int i=head[u];i;i=e[i].nxt){
    			int v=e[i].to,w=e[i].w;
    			if(d[v]||!w)continue;
    			d[v]=d[u]+1,q.push(v);
    			if(v==t)return 1;
    		}
    	}
    	return 0;
    }
    int dinic(int u,int flow){
    	if(u==t)return flow;
    	int rest=flow;
    	for(int i=head[u];i&&rest;i=e[i].nxt){
    		int v=e[i].to,w=e[i].w;
    		if(d[v]!=d[u]+1||!w)continue;
    		int k=dinic(v,min(rest,w));
    		if(!k)d[v]=0; 
    		e[i].w-=k,e[i^1].w+=k,rest-=k;
    	}
    	return flow-rest;
    }
    
    void read_and_parse(){
    	scanf("%d%d%d%d",&n,&m,&s,&t);
    	for(int i=1;i<=m;i++){
    		int x,y,z;
    		scanf("%d%d%d",&x,&y,&z);
    		add_edge(x,y,z),add_edge(y,x,0);
    	}
    }
    void solve(){
    	int now=0;
    	while(bfs())while(now=dinic(s,inf))maxflow+=now;
    	printf("%d
    ",maxflow);
    }
    int main(){
    	read_and_parse();
    	solve();
    	return 0;	
    }
    
  • 相关阅读:
    笔记44 Hibernate快速入门(一)
    tomcat 启用https协议
    笔记43 Spring Security简介
    笔记43 Spring Web Flow——订购披萨应用详解
    笔记42 Spring Web Flow——Demo(2)
    笔记41 Spring Web Flow——Demo
    Perfect Squares
    Factorial Trailing Zeroes
    Excel Sheet Column Title
    Excel Sheet Column Number
  • 原文地址:https://www.cnblogs.com/wzj-xhjbk/p/10765115.html
Copyright © 2011-2022 走看看