• Uva -1515 Pool construction(最小割)


    输入一个字符矩阵,'.'代表洞,'#'代表草地。可以把草改成洞花费为d,或者把洞改成草花费为f,最后还要在草和洞之间修围栏花费为b。

    首先把最外一圈的洞变成草,并累加花费。

    增加一个源点和一个汇点,源点连接每个草地,汇点连接每个洞。

    源点与最外一圈的草地连一条容量无穷大的边,与其他草地连一条容量为d的边。表示把这条弧切断,割的容量增加d,草就会变成洞。

    每个洞与汇点连一条容量为f的边。

    相邻两个格子之间连一条双向边。

    用最大流算法求最小割在加上之前把边界上的洞变成草的费用,就是最小花费。

    用最小的费用将对象划分成两个集合的问题常常可以转换成最小割顺利解决.这道题就可以考虑将每一个点变成草地和洞分成两个集合.

    如果通过合适的建边使得花费的总和等价于割的容量的话,那么为了求最小花费只要求最小割就好.

      1 #include <iostream>
      2 #include <cstdio>
      3 #include <cmath>
      4 #include <vector>
      5 #include <cstring>
      6 #include <string>
      7 #include <algorithm>
      8 #include <string>
      9 #include <set>
     10 #include <functional>
     11 #include <numeric>
     12 #include <sstream>
     13 #include <stack>
     14 #include <map>
     15 #include <queue>
     16 #pragma comment(linker, "/STACK:102400000,102400000")
     17 #define CL(arr, val)    memset(arr, val, sizeof(arr))
     18 
     19 #define ll long long
     20 #define inf 0x7f7f7f7f
     21 #define lc l,m,rt<<1
     22 #define rc m + 1,r,rt<<1|1
     23 #define pi acos(-1.0)
     24 
     25 #define L(x)    (x) << 1
     26 #define R(x)    (x) << 1 | 1
     27 #define MID(l, r)   (l + r) >> 1
     28 #define Min(x, y)   (x) < (y) ? (x) : (y)
     29 #define Max(x, y)   (x) < (y) ? (y) : (x)
     30 #define E(x)        (1 << (x))
     31 #define iabs(x)     (x) < 0 ? -(x) : (x)
     32 #define OUT(x)  printf("%I64d
    ", x)
     33 #define lowbit(x)   (x)&(-x)
     34 #define Read()  freopen("a.txt", "r", stdin)
     35 #define Write() freopen("b.txt", "w", stdout);
     36 #define maxn 1010
     37 #define maxv 3000
     38 #define mod 1000000000
     39 using namespace std;
     40 
     41 struct edge
     42 {
     43     int to,cap,rev;
     44     edge(){}
     45     edge(int x,int y,int z)
     46     {
     47         to=x;
     48         cap=y;
     49         rev=z;
     50     }
     51 };
     52 
     53 vector<edge>G[maxv];
     54 int level[maxv];
     55 int iter[maxv];
     56 
     57 void Add_Edge(int from,int to,int cap)
     58 {
     59     G[from].push_back((edge){to,cap,G[to].size()});
     60     G[to].push_back((edge){from,0,G[from].size()-1});
     61 }
     62 
     63 void bfs(int s)
     64 {
     65     memset(level,-1,sizeof(level));
     66     queue<int>que;
     67     level[s]=0;
     68     que.push(s);
     69     while(!que.empty())
     70     {
     71         int v=que.front();que.pop();
     72         for(int i=0;i<G[v].size();i++)
     73         {
     74             edge &e=G[v][i];
     75             if(e.cap>0&&level[e.to]<0)
     76             {
     77                 level[e.to]=level[v]+1;
     78                 que.push(e.to);
     79             }
     80         }
     81     }
     82 }
     83 int dfs(int v,int t,int f)
     84 {
     85     if(v==t) return f;
     86     for(int &i=iter[v];i<G[v].size();i++)
     87     {
     88         edge &e=G[v][i];
     89         if(e.cap>0&&level[v]<level[e.to])
     90         {
     91             int d=dfs(e.to,t,min(f,e.cap));
     92             if(d>0)
     93             {
     94                 e.cap-=d;
     95                 G[e.to][e.rev].cap+=d;
     96               //  printf("%d %d %d
    ",e.to,e.rev,G[e.to][e.rev]);
     97                 return d;
     98             }
     99         }
    100     }
    101     return 0;
    102 }
    103 
    104 int max_flow(int s,int t)
    105 {
    106     int flow=0;
    107     for(;;)
    108     {
    109         bfs(s);
    110         if(level[t]<0) return flow;
    111         memset(iter,0,sizeof(iter));
    112         int f;
    113         while((f=dfs(s,t,inf))>0)
    114         flow+=f;
    115     }
    116 }
    117 char s[55][55];
    118 int w,h;
    119 int ID(int i,int j)
    120 {
    121     return i*w+j;
    122 }
    123 int main()
    124 {
    125     //freopen("a.txt","r",stdin);
    126     int t,d,f,b;
    127     scanf("%d",&t);
    128     while(t--)
    129     {
    130         scanf("%d%d%d%d%d",&w,&h,&d,&f,&b);
    131         for(int i=0;i<w*h+2;i++)
    132             G[i].clear();
    133         for(int i=0;i<h;i++)
    134         {
    135             scanf("%s",s[i]);
    136         }
    137         int cost=0;
    138         for(int i=0;i<h;i++)
    139         {
    140             if(s[i][0]=='.') {s[i][0]='#';cost+=f;}
    141             if(s[i][w-1]=='.') {s[i][w-1]='#';cost+=f;}
    142         }
    143         for(int i=0;i<w;i++)
    144         {
    145             if(s[0][i]=='.') {s[0][i]='#';cost+=f;}
    146             if(s[h-1][i]=='.'){s[h-1][i]='#';cost+=f;}
    147         }
    148         for(int i=0;i<h;i++)
    149         {
    150             for(int j=0;j<w;j++)
    151             {
    152                 if(s[i][j]=='#')
    153                 {
    154                     int cap=inf;
    155                     if(i>0&&i<h-1&&j>0&&j<w-1) cap=d;
    156                     Add_Edge(w*h,ID(i,j),cap);
    157                     if(i>0) {Add_Edge(ID(i,j),ID(i-1,j),b);}
    158                     if(i<h-1) {Add_Edge(ID(i,j),ID(i+1,j),b);}
    159                     if(j>0) {Add_Edge(ID(i,j),ID(i,j-1),b);}
    160                     if(j<w-1) {Add_Edge(ID(i,j),ID(i,j+1),b);}
    161                 }
    162                 else
    163                 {
    164                     Add_Edge(ID(i,j),w*h+1,f);
    165                     if(i>0) {Add_Edge(ID(i,j),ID(i-1,j),b);}
    166                     if(i<h-1) {Add_Edge(ID(i,j),ID(i+1,j),b);}
    167                     if(j>0) {Add_Edge(ID(i,j),ID(i,j-1),b);}
    168                     if(j<w-1) {Add_Edge(ID(i,j),ID(i,j+1),b);}
    169                 }
    170             }
    171         }
    172         printf("%d
    ",cost+max_flow(w*h,w*h+1));
    173     }
    174     return 0;
    175 }
  • 相关阅读:
    Python 文件批量改名
    解决 unity 生成 android apk read Resources
    IIS 重定向 自动追加 eurl.axd 后缀
    多线程
    zookeeper面试
    线程之间的通信(thread signal)
    软考高项之计算题成本类计算
    PowerDesigner PDM 复制comment到name
    软考高项之计算题进度类
    全面理解Java内存模型
  • 原文地址:https://www.cnblogs.com/nowandforever/p/4603230.html
Copyright © 2020-2023  润新知