博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
网络流——最大流Dinic算法
阅读量:6828 次
发布时间:2019-06-26

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

前言

突然发现到了新的一年什么东西好像就都不会了凉凉

算法步骤

  1. 建残量网络图
  2. 在残量网络图上跑增广路
  3. 重复1直到没有增广路(注意一个残量网络图要尽量把价值都用完,不然会浪费建图的时间)

代码实现

#include
#include
#include
#include
#include
#include
#include
#include
#include
using namespace std;#define ll long long#define re register#define file(a) freopen(a".in","r",stdin);freopen(a".out","w",stdout)inline int gi(){ int f=1,sum=0;char ch=getchar(); while(ch>'9' || ch<'0'){if(ch=='-')f=-1;ch=getchar();} while(ch>='0' && ch<='9'){sum=(sum<<3)+(sum<<1)+ch-'0';ch=getchar();} return f*sum;}const int N=10010,M=100010,Inf=1e9+10;int n,m,s,t,flow;class Graph{private: int front[N],nxt[M<<1],to[M<<1],w[M<<1],cnt,dep[N]; bool bfs(){ queue
Q;while(!Q.empty())Q.pop(); memset(dep,0,sizeof(dep)); Q.push(s);dep[s]=1; while(!Q.empty()){ int u=Q.front();Q.pop(); for(int i=front[u];i!=-1;i=nxt[i]){ int v=to[i]; if(!dep[v] && w[i]){ dep[v]=dep[u]+1;Q.push(v); } } } return dep[t]; } int dfs(int u,int Flow){ if(u==t || !Flow)return Flow; for(int i=front[u];i!=-1;i=nxt[i]){ int v=to[i]; if(dep[v]==dep[u]+1 && w[i]){ int di=dfs(v,min(Flow,w[i])); if(di){ w[i]-=di;w[i^1]+=di; return di; } } } return 0; }public: void Add(int u,int v,int val){to[cnt]=v;nxt[cnt]=front[u];front[u]=cnt;w[cnt]=val;cnt++;} void init(){memset(front,-1,sizeof(front));cnt=0;} void Dinic(){ while(bfs()){ while(int d=dfs(s,Inf)){ flow+=d; } } }}MaxFlow;int main(){ n=gi();m=gi();s=gi();t=gi(); MaxFlow.init(); for(int i=1;i<=m;i++){ int u=gi(),v=gi(),val=gi(); MaxFlow.Add(u,v,val);MaxFlow.Add(v,u,0); } MaxFlow.Dinic(); printf("%d\n",flow); return 0;}

当前弧优化

考虑我们在dfs搜索的时候,是不是有什么东西重复了?

显然搜索过的就不可能再来了(因为已经被压榨干净了)
然后就可以修改一些dfs的过程。

int dfs(int u,int Flow){    if(u==t || !Flow)return Flow;    for(int &i=cur[u];i!=-1;i=nxt[i]){        int v=to[i];        if(dep[v]==dep[u]+1 && w[i]){            int di=dfs(v,min(Flow,w[i]));            if(di){                w[i]-=di;w[i^1]+=di;                return di;            }        }    }    return 0;}void Dinic(){    while(bfs()){        for(int i=1;i<=n;i++)cur[i]=front[i];        while(int d=dfs(s,Inf)){            flow+=d;        }    }}

优化还是比较明显的。

大家可以在看完之后切了

当然陆续将会推出HLPP与ISAP的总结。

转载于:https://www.cnblogs.com/mle-world/p/10253441.html

你可能感兴趣的文章
常用的python模块
查看>>
程序源代码行数分析统计器
查看>>
DNGuard Enterprise v2.80 released
查看>>
[超强]废旧硬盘改造成扬声器!!
查看>>
WPP
查看>>
C# GetSchema Get List of Table 获取数据库中所有的表名以及表中的纪录条数的方法
查看>>
PySide教程:“.NET研究”第一个PySide应用
查看>>
winrar自解压释放路径详解
查看>>
图像开运算+闭运算+腐蚀+膨胀
查看>>
poj-1324 Holedox Moving **** [转]
查看>>
深入foreach工作方式
查看>>
Linux curl使用简单介绍(转)
查看>>
UIView 进行各种动画展示及其用法解释
查看>>
公布2012年5月赛CSDN算法达人赛试题及参考答案
查看>>
Mysql ON子句和USING子句
查看>>
linux杂谈
查看>>
类型、值和变量
查看>>
UIImage+Scale
查看>>
Linux sed 替换第一次出现的字符串
查看>>
windows 下VLC播放器应用之二------LIBVLC API解析
查看>>