zoukankan      html  css  js  c++  java
  • 【BZOJ】1001: [BeiJing2006]狼抓兔子(最小割 / 对偶图)

    题目

    传送门:QWQ

    分析

      显然答案是最小割。

      然后dinic卡一卡过去了。

      其实是懒得写转对偶图:正解

       (dinic原来写的是vector,后来改的比较鬼畜

    代码

    #include <bits/stdc++.h>
    using namespace std;
    const int maxn=1e6+5, INF=2e9;
    struct Edge{
        int from,to,cap,flow;
    };
    int siz=0;
    Edge edges[6*maxn]; int G[maxn][7];
    int que[maxn]; 
    int d[maxn], vis[maxn], cur[maxn];
    int s,t;
    void Addedge(int a,int b,int c){
       // edges.push_back((Edge){a,b,c,0}); edges.push_back((Edge){b,a,c,0});
       // int m=edges.size()-1; G[a].push_back(m-1); G[b].push_back(m);
       edges[siz++]=(Edge){a,b,c,0};  edges[siz++]=(Edge){b,a,c,0};
       G[a][++G[a][0]]=siz-2; G[b][++G[b][0]]=siz-1;
    }
    bool BFS(){
        memset(vis,0,sizeof(vis)); memset(que,0,sizeof(que));
        que[1]=s;
        d[s]=0; vis[s]=1;
        int l=1,r=2;
        while(l<r){
            int x=que[l]; l++;
            for(int i=1;i<=G[x][0];i++){
                Edge v=edges[G[x][i]];
                if(!vis[v.to] && v.flow<v.cap){
                    vis[v.to]=1; d[v.to]=d[x]+1;
                    que[r++]=v.to;
                }
            }
        }
        return vis[t];
    }
    int DFS(int x, int a){
        if(x==t || a==0) return a;
        int flow=0, f;
        for(int& i=cur[x]; i<=G[x][0]; i++){
            Edge& v=edges[G[x][i]];
            if(d[x]+1==d[v.to] && (f=DFS(v.to,min(a,v.cap-v.flow)))){
                v.flow+=f; edges[G[x][i]^1].flow-=f;
                if(!f) {d[v.to]=-1;continue;}
                flow+=f; a-=f;
                if(a==0) break; 
            }
        }
        return flow;
    }
    int Maxflow()
    {
        int flow=0;
        while(BFS()){
            for(int i=0;i<maxn;i++) cur[i]=1;
            flow+=DFS(s,INF);
        }
        return flow;
    }
    inline int getint()
    {
           int w=0,q=0;
           char c=getchar();
           while((c<'0' || c>'9') && c!='-') c=getchar();
           if (c=='-')  q=1, c=getchar();
           while (c>='0' && c<='9') w=w*10+c-'0', c=getchar();
           return q ? -w : w;
    }
     
    int main()
    {
        int n,m; scanf("%d%d",&n,&m);
        if(n==1&&m==1){ puts("0"); return 0; 
        } 
        s=1; t=n*m; 
        int capp;
        for(int i=0;i<n;i++){
            for(int j=1;j<m;j++){
                capp=getint();
                Addedge(i*m+j,i*m+j+1,capp);
        //      printf("*** %d %d %d
    ",i*m+j,i*m+j+1,capp); 
            }
        }
        for(int i=1;i<n;i++){
            for(int j=1;j<=m;j++){
                capp=getint();
                Addedge(m*(i-1)+j,i*m+j,capp);
        //      printf("*** %d %d %d
    ",m*(i-1)+j,i*m+j,capp); 
            }
        } 
        for(int i=1;i<n;i++){
            for(int j=1;j<m;j++){
                capp=getint();
                Addedge(m*(i-1)+j,i*m+j+1,capp);
        //      printf("*** %d %d %d
    ",m*(i-1)+j,i*m+j+1,capp); 
            }
        }
        printf("%d
    ",Maxflow());
        return 0;
    }
  • 相关阅读:
    浅谈聚类算法(K-means)
    多步法求解微分方程数值解
    本学期微分方程数值解课程总结(matlab代码)
    Stone Game
    Two Sum IV
    Insert into a Binary Search Tree
    Subtree of Another Tree
    Leaf-Similar Trees
    Diameter of Binary Tree
    Counting Bits
  • 原文地址:https://www.cnblogs.com/noblex/p/8994749.html
Copyright © 2011-2022 走看看