博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
hihoCoder 1378 网络流二·最大流最小割定理 (网络流学习#2 记录)
阅读量:5135 次
发布时间:2019-06-13

本文共 3698 字,大约阅读时间需要 12 分钟。

题目链接:

 

代码:

#include
using namespace std;const int maxn=505;int c[maxn][maxn],pre[maxn],flow[maxn][maxn],INF=0x3f3f3f3f,n,vis[maxn]={
0},flag=0,num=0;int bfs(int s,int t){ for(int i=1;i<=n;i++) pre[i]=-1; queue
q; q.push(s); int node; if(flag) vis[s]=1,num++; while(!q.empty()) { node=q.front(); q.pop(); for(int i=1;i<=n;i++) { if(flag==0&&pre[i]==-1&&c[node][i]-flow[node][i]>0) { pre[i]=node; if(flag==0&&i==t) return 1; q.push(i); } else if(flag&&pre[i]==-1&&c[node][i]>flow[node][i]) { pre[i]=node; if(vis[i]==0) vis[i]=1,num++; q.push(i); } } } return 0;}int dfs(int node,int v){ if(node==1) return v; v=dfs(pre[node],min(v,c[pre[node]][node]-flow[pre[node]][node])); flow[pre[node]][node]+=v; flow[node][pre[node]]-=v; return v;}int maxflow(int s,int t){ int tmp,ans=0; while(bfs(s,t)) { tmp=dfs(t,INF); ans+=tmp; } return ans;}int main(){ int m; scanf("%d%d",&n,&m); int u,v,cc; for(int i=1;i<=n;i++) for(int j=1;j<=n;j++) c[i][j]=0,flow[i][j]=0; for(int i=1;i<=m;i++) { scanf("%d%d%d",&u,&v,&cc); c[u][v]+=cc; } printf("%d ",maxflow(1,n)); flag=1; flag=bfs(1,n); flag=1; printf("%d\n",num); for(int i=1;i<=n;i++) { if(vis[i]) { if(flag) flag=0; else printf(" "); printf("%d",i); } } puts("");}
View Code

(邻接矩阵版)

 

#include
using namespace std;const int maxn=505,M=20005;struct node{int v,c,flow,nxt;}edge[M*2];int head[maxn],tot,n,vis[maxn],num,flag=0,INF=0x3f3f3f3f;void addnode(int u,int v,int c){ edge[tot].v=v; edge[tot].c=c; edge[tot].flow=0; edge[tot].nxt=head[u]; head[u]=tot++; edge[tot].v=u; edge[tot].c=0; edge[tot].flow=0; edge[tot].nxt=head[v]; head[v]=tot++;}int bfs(){ memset(vis,0,sizeof(vis)); queue
q; q.push(1); vis[1]=1; if(flag) num++; while(!q.empty()) { int tmp=q.front(); q.pop(); for(int i=head[tmp];i!=-1;i=edge[i].nxt) { int c=edge[i].c,v=edge[i].v,f=edge[i].flow; if(vis[v]==0&&c-f>0) { vis[v]=vis[tmp]+1; if(flag==0&&v==n) return 1; if(flag)num++; q.push(v); } } } return 0;}int dfs(int x,int c){ int ans=0; if(x==n||c==0) return c; for(int i=head[x];i!=-1;i=edge[i].nxt) { int v=edge[i].v,cc=edge[i].c,f=edge[i].flow,kk; if(vis[v]==vis[x]+1) { kk=dfs(v,min(cc-f,c)); if(kk>0) { edge[i].flow+=kk; edge[i^1].flow-=kk; ans+=kk; c-=kk; if(c==0) break; } } } return ans;}int maxflow(int s,int t){ int ans=0; while(bfs()) { ans+=dfs(s,INF); } flag=1; flag=bfs(); return ans;}int main(){ int m,u,v,c; tot=0; num=0; scanf("%d%d",&n,&m); for(int i=1;i<=n;i++) head[i]=-1; for(int i=0;i
View Code

 

(邻接表版)

这个好像是当时看了题目一脸懵逼,然后后面看了一眼十佳代码,突然就明白了。。然后手打了两份。

也没仔细看思想是哪一个,之前看sap还是dinic是要分层的,,,看了一堆理论,说是优化ek就优化找增广路径。我想大概这就是所谓的dinic吧。

这题求的是最小割和割完后原点所在的集合点的个数和原点所在集合所有点。

flag就是判断是不是最后一遍搜索,最后一遍bfs就是为了求与s联通的点并标记,计数。

转载于:https://www.cnblogs.com/wwdf/p/5954419.html

你可能感兴趣的文章
实验报告四
查看>>
(简单) HDU 3308 LCIS,线段树+区间合并。
查看>>
智能ABC输入法的三个小秘密
查看>>
MySQL数据库应用 从入门到精通 学习笔记
查看>>
[转载]Ocelot简易教程(二)之快速开始2
查看>>
Understanding Bootstrap Of Oracle Database
查看>>
个人vscode配置汇总
查看>>
jquery table的隔行变色 鼠标事件
查看>>
tensorflow中经典损失函数
查看>>
mybatis-3 最新版本(截止7.2)我们再来看看文档(一)
查看>>
LOG4NET开源日志dll引用流程,在net3.5中已经实践ok
查看>>
UVA 11806 Cheerleaders (容斥原理)
查看>>
Setsockopt选项
查看>>
Integer引用类型问题
查看>>
laravel之数据库
查看>>
MySQL事务与锁
查看>>
20172305 2017-2018-2 《程序设计与数据结构》第一周学习总结
查看>>
Mybatis学习--入门
查看>>
单节点ceph测试环境搭建
查看>>
JavaScript中的Location地址对象
查看>>