zoukankan      html  css  js  c++  java
  • sgu 194 Reactor Cooling(有容量上下界的无源无汇可行流)

    【题目链接】

        http://acm.hust.edu.cn/vjudge/problem/viewProblem.action?id=20757

    【题意】

        求有容量上下界的无源无汇可行流。

    【思路】

        无源无汇可行流要求所有的顶点都满足流量平衡。

        基本思路是转化成最大流来做。

        对于边(u,v,b,c),连边(u,v,c-b)。为了保持流量平衡,我们还需要连边
            1.(S,u,inB[u]-outB[u])  inB>outB

            2.(u,T,outB[u]-inB[u])  outB>inB

        S->T跑一遍最大流,如果S的出边或T的入边满载则有解。

    【代码】

      1 #include<set>
      2 #include<cmath>
      3 #include<queue>
      4 #include<vector>
      5 #include<cstdio>
      6 #include<cstring>
      7 #include<iostream>
      8 #include<algorithm>
      9 #define trav(u,i) for(int i=front[u];i;i=e[i].nxt)
     10 #define FOR(a,b,c) for(int a=(b);a<=(c);a++)
     11 using namespace std;
     12 
     13 typedef long long ll;
     14 const int N = 4e2+10;
     15 const int M = N*N+10;
     16 const int inf = 1e9;
     17 
     18 ll read() {
     19     char c=getchar();
     20     ll f=1,x=0;
     21     while(!isdigit(c)) {
     22         if(c=='-') f=-1; c=getchar();
     23     }
     24     while(isdigit(c))
     25         x=x*10+c-'0',c=getchar();
     26     return x*f;
     27 }
     28 
     29 struct Edge {
     30     int u,v,cap,flow;
     31 };
     32 struct Dinic {
     33     int n,m,s,t;
     34     int d[N],cur[N],vis[N];
     35     vector<int> g[N];
     36     vector<Edge> es;
     37     queue<int> q;
     38     void init(int n) {
     39         this->n=n;
     40         es.clear();
     41         FOR(i,0,n) g[i].clear();
     42     }
     43     void clear() {
     44         FOR(i,0,(int)es.size()-1) es[i].flow=0;
     45     }
     46     void AddEdge(int u,int v,int w) {
     47         es.push_back((Edge){u,v,w,0});
     48         es.push_back((Edge){v,u,0,0});
     49         m=es.size();
     50         g[u].push_back(m-2);
     51         g[v].push_back(m-1);
     52     }
     53     int bfs() {
     54         memset(vis,0,sizeof(vis));
     55         q.push(s); d[s]=0; vis[s]=1;
     56         while(!q.empty()) {
     57             int u=q.front(); q.pop();
     58             FOR(i,0,(int)g[u].size()-1) {
     59                 Edge& e=es[g[u][i]];
     60                 int v=e.v;
     61                 if(!vis[v]&&e.cap>e.flow) {
     62                     vis[v]=1;
     63                     d[v]=d[u]+1;
     64                     q.push(v);
     65                 }
     66             }
     67         }
     68         return vis[t];
     69     }
     70     int dfs(int u,int a) {
     71         if(u==t||!a) return a;
     72         int flow=0,f;
     73         for(int& i=cur[u];i<g[u].size();i++) {
     74             Edge& e=es[g[u][i]];
     75             int v=e.v;
     76             if(d[v]==d[u]+1&&(f=dfs(v,min(a,e.cap-e.flow)))>0) {
     77                 e.flow+=f; 
     78                 es[g[u][i]^1].flow-=f;
     79                 flow+=f; a-=f;
     80                 if(!a) break;
     81             }
     82         }
     83         return flow;
     84     }
     85     int MaxFlow(int s,int t) {
     86         this->s=s,this->t=t;
     87         int flow=0;
     88         while(bfs()) {
     89             memset(cur,0,sizeof(cur));
     90             flow+=dfs(s,inf);
     91         }
     92         return flow;
     93     }
     94 } dc;
     95 
     96 int n,m,sum,B[M],INB[N],OUTB[N];
     97 
     98 int main()
     99 {
    100     n=read(),m=read();
    101     dc.init(n+4);
    102     int S=0,T=n+1;
    103     FOR(i,1,m) {
    104         int u=read(),v=read(),b=read(),c=read();
    105         dc.AddEdge(u,v,c-b);
    106         B[i]=b;
    107         INB[v]+=b,OUTB[u]+=b;
    108     }
    109     FOR(i,1,n) {
    110         int c=INB[i]-OUTB[i];
    111         if(c>0) dc.AddEdge(S,i,c),sum+=c;
    112         else dc.AddEdge(i,T,-c);
    113     }
    114     if(dc.MaxFlow(S,T)!=sum) puts("NO");
    115     else {
    116         puts("YES");
    117         FOR(i,0,m-1) printf("%d
    ",dc.es[i*2].flow+B[i+1]);
    118     }
    119     return 0;
    120 }
  • 相关阅读:
    采集智能电表
    未能写入输出文件“c:\WINDOWS\Microsoft.NET\Framework\.....dll”“拒绝访问。
    随笔写写jquery
    随便写写,,
    写写Ajaxpro
    C# 给程序加日志功能。
    Oracle_Database_11g_标准版_企业版__下载地址_详细列表
    通过C#发送自定义的html格式邮件
    C# 加密解密链接字符串
    获取本地 有线 正在使用的网卡信息
  • 原文地址:https://www.cnblogs.com/lidaxin/p/5313165.html
Copyright © 2011-2022 走看看