zoukankan      html  css  js  c++  java
  • UVA-11082 Matrix Decompressing (网络流建模)

    题目大意:给出一个由1到20组成的整数矩阵的每一行和每一列的和,构造这个矩阵。输出任意一个构造方案。

    题目分析:将每一行视作一个点x,将每一列视作一个点y。对于矩阵中的每一个格子,都对应一个二元关系<x,y>,从x连一条有向弧到y,容量置为19。增加源点s和汇点t,对于每一个x,连一条从s到x的有向弧,容量置为对应的该行总和减去列数,对于每一个y,连一条从y到t的有向弧,容量置为对应的该列总和减去行数。对于这个寻找最大流,算法终止后,如果从s出发的每一条弧和到达t的每一条弧都是饱和的,那么每一个xi到yj的流量便是对应格子中的值减一;否则,无解。这道题,一定有解。  显然,这样建模是正确的。

    代码如下:

    # include<iostream>
    # include<cstdio>
    # include<cmath>
    # include<string>
    # include<vector>
    # include<list>
    # include<set>
    # include<map>
    # include<queue>
    # include<cstring>
    # include<algorithm>
    using namespace std;
    
    # define LL long long
    # define REP(i,s,n) for(int i=s;i<n;++i)
    # define CL(a,b) memset(a,b,sizeof(a))
    # define CLL(a,b,n) fill(a,a+n,b)
    
    const double inf=1e30;
    const int INF=1<<30;
    const int N=1000;
    
    struct Edge
    {
        int fr,to,cap,flow;
        Edge(int _fr,int _to,int _cap,int _flow):fr(_fr),to(_to),cap(_cap),flow(_flow){}
    };
    vector<Edge>edge;
    int id[50][50],r,c,a[25],b[25],f[50],p[50];
    vector<int>G[50];
    
    void init()
    {
        a[0]=b[0]=0;
        REP(i,0,r+c+2) G[i].clear();
        edge.clear();
    }
    
    void addEdge(int fr,int to,int cap)
    {
        edge.push_back(Edge(fr,to,cap,0));
        edge.push_back(Edge(to,fr,0,0));
        int m=edge.size();
        id[fr][to]=m-2;
        G[fr].push_back(m-2);
        G[to].push_back(m-1);
    }
    
    void maxFlow(int s,int t)
    {
        while(1)
        {
            queue<int>q;
            CL(f,0);
            f[s]=INF;
            q.push(s);
            while(!q.empty()){
                int u=q.front();
                q.pop();
                REP(i,0,G[u].size()){
                    Edge &e=edge[G[u][i]];
                    if(!f[e.to]&&e.cap>e.flow){
                        p[e.to]=G[u][i];
                        f[e.to]=min(f[u],e.cap-e.flow);
                        q.push(e.to);
                    }
                }
                if(f[t]) break;
            }
            if(!f[t]) break;
            for(int u=t;u!=s;u=edge[p[u]].fr){
                edge[p[u]].flow+=f[t];
                edge[p[u]^1].flow-=f[t];
            }
        }
    }
    
    int main()
    {
        int T,cas=0;
        scanf("%d",&T);
        while(T--)
        {
            scanf("%d%d",&r,&c);
            init();
            REP(i,1,r+1) scanf("%d",a+i);
            REP(i,1,c+1) scanf("%d",b+i);
            REP(i,1,r+1) addEdge(0,i,a[i]-a[i-1]-c);
            REP(i,1,r+1) REP(j,r+1,r+c+1) addEdge(i,j,19);
            REP(i,r+1,r+c+1) addEdge(i,r+c+1,b[i-r]-b[i-r-1]-r);
            maxFlow(0,r+c+1);
            printf("Matrix %d
    ",++cas);
            REP(i,1,r+1) REP(j,1,c+1) printf("%d%c",edge[id[i][j+r]].flow+1,(j==c)?'
    ':' ');
            if(T) printf("
    ");
        }
      return 0;
    }
    

      

  • 相关阅读:
    李永乐,皇帝的新衣背后,共有知识和公共知识
    汇率原理
    mybatis pageHelper 分页插件使用
    oracle中的exists 和not exists 用法详解
    Webservice入门简单实例
    java-可逆加密算法
    idea 卡顿问题
    idea svn操作
    HttpServletrequest 与HttpServletResponse总结
    Spring boot中应用jpa jpa用法
  • 原文地址:https://www.cnblogs.com/20143605--pcx/p/5011647.html
Copyright © 2011-2022 走看看