奥里给,如果下次看自己解释的这篇dinic看不懂的时候,告诉自己,网络流是板子,会建图就行。
const int N=210000;
struct node
{
int to,cap,next;
} p[N*10];
int dis[N];
int head[N];
int cnt=-1;
queue<int> q;
void add(int from,int to,int cap)
{
cnt++;
p[cnt].to=to;
p[cnt].cap=cap;
p[cnt].next=head[from];
head[from]=cnt;
}
bool bfs(int s,int t)//分层,可以当做求树的深度理解
{
q=queue<int>();
memset(dis,-1,sizeof(dis));
dis[s]=0;
q.push(s);
while(!q.empty())
{
int x=q.front();
q.pop();
for(int i=head[x]; i!=-1; i=p[i].next)
{
int now=p[i].to;
if(dis[now]==-1&&p[i].cap!=0)
{
dis[now]=dis[x]+1;
q.push(now);
}
}
}
return dis[t]!=-1;
}
int dfs(int x,int t,int maxflow)//maxflow表示流入当前点的流量
{
if(x==t)return maxflow;
int ans=0;
for(int i=head[x]; i!=-1; i=p[i].next)
{
int now=p[i].to;
if(dis[now]!=dis[x]+1||p[i].cap==0||ans==maxflow) continue;
int f=dfs(now,t,min(p[i].cap,maxflow-ans));//每次dfs的第三个变量都是在当前这个点的可以流出的量(此量每次到for循环的下一层循环的时候都会变小或者不变)和当前流出边的cap取最小值。
p[i].cap-=f;
p[i^1].cap+=f;
ans+=f;
}
return ans;//如此递归下去
}
int dinic(int s,int t)
{
int ans=0;
while(bfs(s,t))//如果还有增广路就dfs
{
ans+=dfs(s,t,9999999999);
}
return ans;
}
//加边加边加边。。。。。。
cout<<dinic(s,t);
时隔多日
dinic当前弧优化版本
struct node
{
int to,cap,next;
} p[N*10];
int dis[N];
int head[N];
int cnt=-1;
queue<int> q;
int cur[N];
void add(int from,int to,int cap)
{
cnt++;
p[cnt].to=to;
p[cnt].cap=cap;
p[cnt].next=head[from];
head[from]=cnt;
}
bool bfs(int s,int t)//分层,可以当做求树的深度理解
{
q=queue<int>();
memset(dis,-1,sizeof(dis));
dis[s]=0;
q.push(s);
cur[s]=head[s];
while(!q.empty())
{
int x=q.front();
q.pop();
if(x==t)return 1;
cur[x]=head[x];
for(int i=head[x]; i!=-1; i=p[i].next)
{
int now=p[i].to;
if(dis[now]==-1&&p[i].cap!=0)
{
dis[now]=dis[x]+1;
q.push(now);
cur[now]=head[now];
}
}
}
return dis[t]!=-1;
}
int dfs(int x,int t,int maxflow)//maxflow表示流入当前点的流量
{
if(x==t)return maxflow;
int ans=0;
for(int i=cur[x]; i!=-1; i=p[i].next)
{
cur[x]=i;
int now=p[i].to;
if(dis[now]!=dis[x]+1||p[i].cap==0||ans==maxflow) continue;
int f=dfs(now,t,min(p[i].cap,maxflow-ans));//每次dfs的第三个变量都是在当前这个点的可以流出的量(此量每次到for循环的下一层循环的时候都会变小或者不变)和当前流出边的cap取最小值。
p[i].cap-=f;
p[i^1].cap+=f;
ans+=f;
if(ans==maxflow)
return ans;
}
return ans;//如此递归下去
}
int dinic(int s,int t)
{
int ans=0;
while(bfs(s,t))//如果还有增广路就dfs
{
ans+=dfs(s,t,9999999999);
}
return ans;
}
int main()
{
int n,m;
cin>>n>>m;
int x,y,c;
memset(head,-1,sizeof head);
while(m--)
{
cin>>x>>y>>c;
add(x,y,c);
add(y,x,0);
}
cout<<dinic(1,n);
return 0;
}