模板 · ISAP网络流+GAP优化+弧优化

//ISAP+GAP优化+弧优化
#include <bits/stdc++.h>
using namespace std;
const int INF = 0x7f7f7f7f;
struct Edge{int from, to, f;};

int n, m, s, t, ct=1;
int Hed[10005], Nex[2*100005], Cur[10005], Dep[10005], Num[10005], Pre[10005];
Edge E[2*100005];

void Add(int &a, int &b, int &f){
	E[++ct].from=a, E[ct].to=b, E[ct].f=f, Nex[ct]=Hed[a], Hed[a]=ct;
	E[++ct].from=b, E[ct].to=a, E[ct].f=0, Nex[ct]=Hed[b], Hed[b]=ct;
}
void BFS(){
	queue<int> Q;
	memset(Dep, 0, sizeof Dep);
	Dep[t] = 1;  Q.push(t);
	int k;
	while(!Q.empty()){
		k = Q.front(); Q.pop();
		Num[Dep[k]]++;
		for(int i=Hed[k]; i; i=Nex[i]){
			if(E[i^1].f && !Dep[E[i].to]){
				Dep[E[i].to] = Dep[k]+1;
				Q.push(E[i].to);
			}
		}
	}
}
int Agument(){
	int k = t, flow = INF;
	while(k != s){
		if(E[Pre[k]].f < flow) flow = E[Pre[k]].f;
		k = E[Pre[k]].from;
	}
	k = t;
	while(k != s){
		E[Pre[k]].f -= flow;
		E[Pre[k]^1].f += flow;
		k = E[Pre[k]].from;
	}
	return flow;
}
int ISAP(int maxdep){
	int flow = 0, k = s, mindep;
	BFS();
	memcpy(Cur, Hed, sizeof Hed);
	bool can;
	while(Dep[s] <= maxdep){
		if(k == t){
			flow += Agument();
			k = s;
		}
		can = 0;
		for(int i=Cur[k]; i; i=Nex[i]){
			if(E[i].f && Dep[E[i].to]+1==Dep[k]){
				can = 1;
				Pre[E[i].to] = i;
				Cur[k] = i;
				k = E[i].to;
				break;
			}
		}
		if(!can){
			mindep = n+1;
			for(int i=Hed[k]; i; i=Nex[i])
				if(Dep[E[i].to]<mindep && E[i].f)
					mindep = Dep[E[i].to];

			if(!--Num[Dep[k]]) break;
			Num[Dep[k]=mindep+1]++;
			Cur[k] = Hed[k];
			if(k != s) k = E[Pre[k]].from;
		}
	}
	return flow;
}
int main(){
	scanf("%d%d%d%d", &n, &m, &s, &t);
	int u, v, c;
	for(int i=1; i<=m; ++i){
		scanf("%d%d%d", &u, &v, &c);
		Add(u, v, c);
	}
	printf("%d", ISAP(n));
	return 0;
}
posted @ 2019-02-05 23:02  Nelson_Wang  阅读(421)  评论(0编辑  收藏  举报