HDU-4280 Island Transport
阿新 • • 發佈:2018-11-10
最大流的板子題,但是資料量比較大,所以用ISAP演算法+bfs初始化+棧優化
#include<iostream> #include<cstdio> #include<cstring> #include<algorithm> #include<cmath> using namespace std; typedef long long ll; const int N=1e5+10; const int M=2e5+10; const int INF=0x7f7f7f7f; struct Edge { int to,nxt,cap,flow; }edge[M]; int tot,first[N]; void addedge(int u,int v,int w,int rw=0) { edge[tot].to=v;edge[tot].cap=w;edge[tot].flow=0; edge[tot].nxt=first[u];first[u]=tot++; edge[tot].to=u;edge[tot].cap=rw;edge[tot].flow=0; edge[tot].nxt=first[v];first[v]=tot++; } void init() { tot=0; memset(first,-1,sizeof(first)); } int gap[N],dep[N],cur[N]; int Q[N],S[N]; void bfs(int s) { int q0=0,q1=0; Q[q1++]=s; memset(gap,0,sizeof(gap)); memset(dep,-1,sizeof(dep)); dep[s]=0; gap[0]=1; while(q0<q1) { int u=Q[q0++]; for(int i=first[u];i!=-1;i=edge[i].nxt) { int v=edge[i].to; if(dep[v]!=-1) continue; dep[v]=dep[u]+1; gap[dep[v]]++; Q[q1++]=v; } } } int sap(int s,int t,int n) { int ans=0; bfs(t); int top=0,inser; memcpy(cur,first,sizeof(first)); int u=s; gap[0]=n; while(dep[s]<n) { if(u==t) { int Min=INF; for(int i=0;i<top;i++) if(Min>edge[S[i]].cap-edge[S[i]].flow) { Min=edge[S[i]].cap-edge[S[i]].flow; inser=i; } for(int i=0;i<top;i++) { edge[S[i]].flow+=Min; edge[S[i]^1].flow-=Min; } ans+=Min; top=inser; u=edge[S[top]^1].to; } bool flag=false; int v; for(int i=cur[u];i!=-1;i=edge[i].nxt) { v=edge[i].to; if(edge[i].cap-edge[i].flow&&dep[v]+1==dep[u]) { flag=true; cur[u]=S[top++]=i; break; } } if(flag) { u=v; continue; } gap[dep[u]]--; if(!gap[dep[u]]) return ans; int Min=n; for(int i=first[u];i!=-1;i=edge[i].nxt) if(edge[i].cap-edge[i].flow&&Min>dep[edge[i].to]) { Min=dep[edge[i].to]; cur[u]=i; } dep[u]=Min+1; gap[dep[u]]++; if(u!=s) u=edge[S[--top]^1].to; } return ans; } int main() { int T; int n,m,a,b,c; int s,t,me,mw; scanf("%d",&T); while(T--) { init(); scanf("%d%d",&n,&m); me=-1000000;mw=1000000; for(int i=1;i<=n;i++) { scanf("%d%d",&a,&b); if(a<mw) { mw=a; s=i; } if(a>me) { me=a; t=i; } } for(int i=1;i<=m;i++) { scanf("%d%d%d",&a,&b,&c); addedge(a,b,c,c); } printf("%d\n",sap(s,t,n)); } return 0; }