[Explanations] grid access issue (network flow)

Grid access issues

Consider this requirement, "there is no common edge," like most of the minimum cut.

Minimum cut: FIG accordance \ (S \) and \ (T \) is divided into two mutually disjoint sets and deleting such an element (side) and minimum weight.

Then we look at this question, first to determine the classification and \ (S \) together and and \ (T \) together point. Apparently due to the opposition of neighboring points it is directly adjacent so we even \ (inf \) side indicates that the neighbor relationship can not be changed . Thus this edge in the minimum cut will not bepigeonOut.

We first drawing in black and white coloring, the connection between the adjacent black and white dots \ (inf \) side, we can change the state of a point in the set is not in the inside, so we make provisions black even \ (S \) , even white \ (T \) , the right side is the right point, this point on behalf of this side exists. Now requires neighboring point can not exist and the least costly, so the rest of the maximum number of direct cut to the minimum.

Said a lot of trouble actually

Figure of black and white coloring, the connection between the adjacent black and white dots \ (inf \) side, we can change the state of a point in the set is not in the inside, so we make provisions black even \ (S \) , even white \ ( T \) , the right side is the point of the right to run the minimum cut.

The relationship between one or the other is the minimum cut it

#include<cstdio>
#include<cstring>
#include<algorithm>
#include<queue>

using namespace std;  typedef long long ll;
inline int qr(){
      register int ret=0,f=0;
      register char c=getchar();
      while(c<48||c>57)f|=c==45,c=getchar();
      while(c>=48&&c<=57) ret=ret*10+c-48,c=getchar();
      return f?-ret:ret;
}
const int maxn=1e2+5;
int id[maxn][maxn];
int nodecnt;
int cnt(1),S,T;
struct E{
      int to,nx,w;
      E(){to=nx=w=0;}
      E(const int&a,const int&b,const int&c){to=a;nx=b;w=c;}
}e[(maxn*maxn)<<4|1];
int head[maxn*maxn];
inline void add(const int&fr,const int&to,const int&w,const bool&f){
      //printf("fr=%d to=%d w=%d f=%d\n",fr,to,w,f);
      if(!(fr&&to))return;
      e[++cnt]=E(to,head[fr],w);
      head[fr]=cnt;
      if(f)add(to,fr,0,0);
}

queue< int > q;
int d[maxn*maxn];
int cur[maxn*maxn],sum;
const int inf=0x3f3f3f3f;
inline bool bfs(){
      for(register int t=1;t<=nodecnt;++t) d[t]=0,cur[t]=head[t];
      q.push(S);
      d[S]=1;
      while(q.size()){
        register int now=q.front();
        q.pop();
        for(register int t=head[now];t;t=e[t].nx){
          if(e[t].w>0&&!d[e[t].to]){
            d[e[t].to]=d[now]+1;
            q.push(e[t].to);
          }
        }
      }
      return d[T];      
}

int dfs(const int&now,int fl){
      if(now==T||fl==0)return fl;
      int ret=0;
      for(register int &t=cur[now];t&&fl;t=e[t].nx){
        if(d[e[t].to]==d[now]+1&&e[t].w>0){
          int d=dfs(e[t].to,min(fl,e[t].w));
          fl-=d;ret+=d;e[t].w-=d;e[t^1].w+=d;
        }
      }
      return ret;
}

inline int dinic(){
      int ret=0;
      while(bfs())ret+=dfs(S,inf);
      return ret;      
}

int main(){
#ifndef ONLINE_JUDGE
      freopen("in.in","r",stdin);
      //freopen("out.out","w",stdout);
#endif
      int n,m;
      n=qr();m=qr();
      for(register int t=1;t<=n;++t)
        for(register int i=1;i<=m;++i)
          id[t][i]=++nodecnt;
      S=++nodecnt;T=++nodecnt;
      for(register int t=1;t<=n;++t){
        for(register int i=1,t1;i<=m;++i){
          //cout<<((t&1)^(i^1)&1^1)<<' ';
          sum+=(t1=qr());
          if((t&1)^(i^1)&1)
            add(id[t][i],T,t1,1);
          if((t&1)^(i^1)&1^1){
            add(S,id[t][i],t1,1);
            add(id[t][i],id[t-1][i],inf,1);add(id[t][i],id[t+1][i],inf,1);
            add(id[t][i],id[t][i+1],inf,1);add(id[t][i],id[t][i-1],inf,1);
          }
        }                        
      }
      printf("%d\n",sum-dinic());
      return 0;
}

Guess you like

Origin www.cnblogs.com/winlere/p/11234629.html