基础网络流学习笔记

Posted lovely_lazy_tag

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了基础网络流学习笔记相关的知识,希望对你有一定的参考价值。

 

以前太naive了,对着蓝书写vector存边,常数惊人。

今天拿链表重写了一遍。

话说把结果输出写到析构函数里好好玩,可以调戏同学:

“喂,你看啊,我的程序没输出喔~”

(掩面)

 

Dinic:

 

  1 #include<cstdio>
  2 #include<queue>
  3 
  4 #define INF 0x3f3f3f3f
  5 #define MAXN 10005
  6 #define MAXM 100005
  7 
  8 #define minn(a,b) ((a)<(b)?(a):(b))
  9 
 10 int n,m;
 11 
 12 struct Dinic{
 13     int s,t;
 14     
 15     int flow,cost;
 16     int cnt,head[MAXN],next[MAXM<<1|1];
 17     int dis[MAXN],cur[MAXN];
 18     
 19     std::queue<int> Q;
 20     
 21     struct Edge{
 22         int u,v,c,f;
 23         
 24         Edge(){}
 25         Edge(int u,int v,int c,int f):u(u),v(v),c(c),f(f){}
 26     }e[MAXM<<1|1];
 27     
 28     Dinic(){
 29         for(int i=0;i<MAXN;++i) head[i]=-1;
 30     }
 31     ~Dinic(){
 32         printf("%d\\n",flow);
 33     }
 34     
 35     inline void addedge(int u,int v,int c){
 36         e[cnt]=Edge(u,v,c,0);
 37         next[cnt]=head[u];
 38         head[u]=cnt++;
 39         
 40         e[cnt]=Edge(v,u,0,0);
 41         next[cnt]=head[v];
 42         head[v]=cnt++;
 43     }
 44     
 45     inline bool BFS(){
 46         for(int i=0;i<=n;++i) dis[i]=0;
 47         dis[s]=1,Q.push(s);
 48         
 49         while(Q.empty()==false){
 50             int u=Q.front();
 51             Q.pop();
 52             
 53             for(int i=head[u];i!=-1;i=next[i]){
 54                 Edge &ed=e[i];
 55                 
 56                 if(ed.c>ed.f&&dis[ed.v]==0)
 57                     dis[ed.v]=dis[u]+1,Q.push(ed.v);
 58             }
 59         }
 60         
 61         return dis[t];
 62     }
 63     
 64     int DFS(int u,int res){
 65         if(u==t||res==0) return res;
 66         
 67         int fff=0;
 68         for(int &i=cur[u];i!=-1;i=next[i]){
 69             Edge &ed=e[i];
 70             
 71             if(ed.c>ed.f&&dis[u]+1==dis[ed.v]){
 72                 int f=DFS(ed.v,minn(ed.c-ed.f,res));
 73                 
 74                 fff+=f,res-=f;
 75                 ed.f+=f,e[i^1].f-=f;
 76                 
 77                 if(res==0) break;
 78             }
 79         }
 80         
 81         return fff;
 82     }
 83     
 84     void solve(){
 85         while(BFS()){
 86             for(int i=0;i<=n;++i) cur[i]=head[i];
 87             flow+=DFS(s,INF);
 88         }
 89     }
 90 };
 91 
 92 Dinic a;
 93 
 94 int main(){
 95     scanf("%d%d%d%d",&n,&m,&a.s,&a.t);
 96     
 97     register int x,y,z;
 98     for(register int i=0;i<m;++i){
 99         scanf("%d%d%d",&x,&y,&z);
100         a.addedge(x,y,z);
101     }
102     
103     a.solve();
104     
105     return 0;
106 }

 

 

MCMF:

 

  1 #include<cstdio>
  2 #include<queue>
  3 
  4 #define INF 0x3f3f3f3f
  5 #define MAXN 5005
  6 #define MAXM 50005
  7 
  8 #define minn(a,b) ((a)<(b)?(a):(b))
  9 
 10 int n,m;
 11 
 12 struct MCMF{
 13     int s,t;
 14     
 15     int flow,cost;
 16     int cnt,head[MAXN],next[MAXM<<1|1];
 17     int dis[MAXN],res[MAXN],pre[MAXN];
 18     
 19     bool inq[MAXN];
 20     
 21     std::queue<int> Q;
 22     
 23     struct Edge{
 24         int u,v,c,f,cost;
 25         
 26         Edge(){}
 27         Edge(int u,int v,int c,int f,int cost):u(u),v(v),c(c),f(f),cost(cost){}
 28     }e[MAXM<<1|1];
 29     
 30     MCMF(){
 31         for(int i=0;i<=MAXN;++i) head[i]=-1;
 32     }
 33     ~MCMF(){
 34         printf("%d %d\\n",flow,cost);
 35     }
 36     
 37     inline void addedge(int u,int v,int c,int cost){
 38         e[cnt]=Edge(u,v,c,0,cost);
 39         next[cnt]=head[u];
 40         head[u]=cnt++;
 41         
 42         e[cnt]=Edge(v,u,0,0,-cost);
 43         next[cnt]=head[v];
 44         head[v]=cnt++;
 45     }
 46     
 47     inline bool SPFA(){
 48         for(int i=0;i<=n;++i) dis[i]=INF,inq[i]=false;
 49         dis[s]=0,inq[s]=true,res[s]=INF,Q.push(s);
 50         
 51         while(Q.empty()==false){
 52             int u=Q.front();
 53             Q.pop(),inq[u]=false;
 54             
 55             for(int i=head[u];i!=-1;i=next[i]){
 56                 Edge &ed=e[i];
 57                 
 58                 if(ed.c>ed.f&&dis[ed.v]>dis[u]+ed.cost){
 59                     dis[ed.v]=dis[u]+ed.cost;
 60                     res[ed.v]=minn(ed.c-ed.f,res[u]);
 61                     pre[ed.v]=i;
 62                     
 63                     if(!inq[ed.v])
 64                         Q.push(ed.v),inq[ed.v]=true;
 65                 }
 66             }
 67         }
 68         
 69         if(dis[t]==INF) return false;
 70         
 71         flow+=res[t];
 72         cost+=res[t]*dis[t];
 73         
 74         for(int u=t;u!=s;u=e[pre[u]].u){
 75             e[pre[u]].f+=res[t];
 76             e[pre[u]^1].f-=res[t];
 77         }
 78         
 79         return true;
 80     }
 81     
 82     inline void solve(){
 83         while(SPFA());
 84     }
 85 };
 86 
 87 MCMF a;
 88 
 89 int main(){
 90     scanf("%d%d%d%d",&n,&m,&a.s,&a.t);
 91     
 92     register int u,v,c,cost;
 93     for(int i=1;i<=m;++i){
 94         scanf("%d%d%d%d",&u,&v,&c,&cost);
 95         a.addedge(u,v,c,cost);
 96     }
 97     
 98     a.solve();
 99     
100     return 0;
101 }

 

以上是关于基础网络流学习笔记的主要内容,如果未能解决你的问题,请参考以下文章

go语言学习笔记 — 基础 — 控制流:流程控制

python爬虫学习笔记-M3U8流视频数据爬虫

DOM探索之基础详解——学习笔记

学习笔记:网络流

201555332盛照宗—网络对抗实验1—逆向与bof基础

算法学习笔记(8.1): 网络最大流算法 EK, Dinic, ISAP