学了一下午网络流,AC了这道模板题
勉强算是自己敲的,debug时参照了下模板,模板参照kuangbin大神
邻接表+isap算法
#include <stdio.h>
#include <string.h>
#define MAXN 210
#define MAXM 420
#define INF 0x3f3f3f3f
struct node{
int to,next,cap;
}edge[MAXM];
int cnt,head[MAXN];
int dis[MAXN],gap[MAXN],cur[MAXN],path[MAXN],queue[MAXN];
void addedge(int u,int v,int w)
{
edge[cnt].to=v;
edge[cnt].cap=w;
edge[cnt].next=head[u];
head[u]=cnt++;
edge[cnt].to=u;
edge[cnt].cap=0;
edge[cnt].next=head[v];
head[v]=cnt++;
}
void bfs(int start,int end)
{
memset(dis,-1,sizeof(dis));
memset(gap,0,sizeof(gap));
int front,rear;
front=rear=0;
queue[rear++]=end;
dis[end]=0;
gap[0]=1;
while(front<rear)
{
int i,v,u=queue[front];
for(i=head[u];i!=-1;i=edge[i].next)
{
v=edge[i].to;
if(dis[v]!=-1)
continue;
queue[rear++]=v;
dis[v]=dis[u]+1;
gap[dis[v]]++;
}
front++;
}
}
int sap(int start,int end,int N)
{
bfs(start,end);
memcpy(cur,head,sizeof(head));
int top=0;
int u=start;
int ans=0;
while(dis[start]<N)
{
if(u==end)
{
int i,inser,min=INF;
for(i=0;i<top;i++)
if(min>edge[path[i]].cap)
{
min=edge[path[i]].cap;
inser=i;
}
for(i=0;i<top;i++)
{
edge[path[i]].cap-=min;
edge[path[i]^1].cap+=min;
}
ans+=min;
top=inser;
u=edge[path[top]^1].to;
continue;
}
int i,v,flag=0;
for(i=cur[u];i!=-1;i=edge[i].next)
{
v=edge[i].to;
if(edge[i].cap&&dis[v]+1==dis[u])
{
flag=1;
cur[u]=path[top++]=i;
u=v;
break;
}
}
if(flag)
continue;
int min=N;
for(i=head[u];i!=-1;i=edge[i].next)
{
v=edge[i].to;
if(edge[i].cap&&dis[v]<min)
{
min=dis[v];
cur[u]=i;
}
}
gap[dis[u]]--;
if(!gap[dis[u]])
return ans;
dis[u]=min+1;
gap[dis[u]]++;
if(start!=u)
u=edge[path[--top]^1].to;
}
return ans;
}
int main()
{
int N,M,u,v,w;
while(scanf("%d%d",&N,&M)!=EOF)
{
cnt=0;
memset(head,-1,sizeof(head));
while(N--)
{
scanf("%d%d%d",&u,&v,&w);
addedge(u,v,w);
}
printf("%d\n",sap(1,M,M));
}
return 0;
}