zoukankan      html  css  js  c++  java
  • 排涝 网络流--最大流 ek算法

    传送门

    以前没接触过最大流问题,刚开始以为是用kruscal算法求最小生成树呢,并且题上也是显示最小树的专题: 

    反正还行吧,捣鼓了两天,总算稍微理解了一下,等会回来整理一下知识点。

     1 #include <iostream>
     2 #include <queue>
     3 #include <algorithm>
     4 #include <cstring>
     5 #include <cstdio>
     6 using namespace std;
     7 const int N=201;
     8 int maxData=1<<30;
     9 int capacity[N][N];//记录残留网络的容量:
    10 int flow[N];       //标记从源点到当前节点可以通过的流量
    11 int pre[N];        //标记在这条路径上当前节点的前驱,同时标记该节点是否在队列中
    12 int n,m;
    13 queue<int> q;
    14 int bfs(int src,int des)    //找增广路径
    15 {
    16     int i,j;
    17     while(!q.empty())//清空队列
    18         q.pop();
    19     for(i=1;i<m+1;i++)
    20         pre[i]=-1;
    21     pre[src]=0;
    22     flow[src]=maxData;
    23     q.push(src);
    24     while(!q.empty())
    25     {
    26         int index=q.front();
    27         q.pop();
    28         if(index==des)      //找到增广路径
    29             break;
    30         for(i=1;i<=m;i++)
    31             if(/*i!=src&&*/ capacity[index][i]>0&&pre[i]==-1)
    32             {
    33                 pre[i]=index;//记录前驱
    34                 flow[i]=min(capacity[index][i],flow[index]);//关键:迭代的找到增量
    35                 q.push(i);
    36             }
    37     }
    38     if(pre[des]==-1)//残留图中不再存在增广路径
    39         return -1;
    40     else
    41         return flow[des];
    42 }
    43 
    44 int maxFlow(int src,int des) //求最大流
    45 {
    46     int increasement=0;
    47     int sumflow=0;
    48     while((increasement=bfs(src,des))!=-1)
    49     {
    50         int k=des;//利用前驱寻找路径
    51         while(k!=src)
    52         {
    53             int last =pre[k];
    54             capacity[last][k]-=increasement;//改变正向的容量
    55             capacity[k][last]+=increasement;//改变反向的容量
    56             k=last;
    57         }
    58         sumflow+=increasement;
    59     }
    60     return sumflow;
    61 }
    62 
    63 int main()
    64 {
    65     int i,j;
    66     int start,end,ci;
    67     while(~scanf("%d%d",&n,&m))
    68     {
    69         memset(capacity,0,sizeof(capacity));
    70         memset(flow,0,sizeof(flow));
    71         for(i=0;i<n;i++)
    72         {
    73             scanf("%d%d%d",&start,&end,&ci);
    74             capacity[start][end]+=ci;//注意可能出现多条同一起点终点的情况
    75         }
    76         printf("%d
    ",maxFlow(1,m));
    77     }
    78     return 0;
    79 }
    80     
  • 相关阅读:
    POJ 1703 Find them, Catch them
    POJ 2236 Wireless Network
    POJ 2010 Moo University
    POJ 2184 Cow Exhibition
    POJ 3280 Cheapest Palindrome
    POJ 3009 Curling 2.0
    POJ 3669 Meteor Shower
    POJ 2718 Smallest Difference
    POJ 3187 Backward Digit Sums
    POJ 3050 Hopscotch
  • 原文地址:https://www.cnblogs.com/WDKER/p/5486808.html
Copyright © 2011-2022 走看看