zoukankan      html  css  js  c++  java
  • BZOJ_3503_[Cqoi2014]和谐矩阵_高斯消元

    BZOJ_3503_[Cqoi2014]和谐矩阵_高斯消元

    题意:

    我们称一个由0和1组成的矩阵是和谐的,当且仅当每个元素都有偶数个相邻的1。一个元素相邻的元素包括它本身,及他上下左右的4个元素(如果存在)。给定矩阵的行数和列数,请计算并输出一个和谐的矩阵。注意:所有元素为0的矩阵是不允许的。

    分析:

    设n*m个未知数,列n*m个方程

    高斯消元解方程,注意全零矩阵不合法

    那我们如果发现有自由元就将它们置为1就好了

    代码:

    #include <stdio.h>
    #include <string.h>
    #include <algorithm>
    #include <queue>
    using namespace std;
    #define p(x,y) ((x-1)*m+y)
    int a[1700][1700];
    int n,m;
    int tx[]={-1,0,0,0,1};
    int ty[]={0,-1,0,1,0};
    int which[1700*1700],ins[1700*1700];
    void build(){
        int i,j,k;
        for(i=1;i<=n;i++){
            for(j=1;j<=m;j++){
                for(k=0;k<5;k++){
                    int dx=i+tx[k],dy=j+ty[k];
                    if(dx>=1&&dx<=n&&dy>=1&&dy<=m){
                        a[p(i,j)][p(dx,dy)]=1;
                    }
                }
            }
        }
    }
    void Guass(){
        int i=1,j=1,k,p;
        while(i<=n*m&&j<=n*m){
            for(k=i;k<=n*m;k++){
                if(a[k][j])break;
            }
            if(a[k][j]){
                if(k!=i){
                    for(p=j;p<=n*m+1;p++){
                        swap(a[k][p],a[i][p]);
                    }
                }
                for(k=i+1;k<=n*m;k++){
                    if(a[k][j]){
                        for(p=j;p<=n*m+1;p++){
                            a[k][p]^=a[i][p];
                        }
                    }
                }
                which[i]=j;
                ins[j]=i;
                i++;
            }
            j++;
        }
        if(i>n*m)return ;
        int id=i;
        for(k=1;k<=n*m;k++){
            if(!ins[k]){
                which[id]=k;
                ins[k]=id++;
            }
        }
        for(k=i;k<=n*m;k++){
            a[k][n*m+1]=1;
        }
        for(k=i-1;k;k--){
            for(p=which[k]+1;p<=n*m;p++){
                if(a[k][p]){
                    a[k][n*m+1]^=a[ins[p]][n*m+1];
                }
            }
        }
    }
    int main(){
        scanf("%d%d",&n,&m);
        build();
        Guass();
        int i,j;
        for(i=1;i<=n;i++){
            int f=0;
            for(j=1;j<=m;j++){
                if(!f)f=
                printf("%d",a[ins[p(i,j)]][n*m+1]);
            else printf(" %d",a[ins[p(i,j)]][n*m+1]);
            }
            puts("");
        }
    }
    
  • 相关阅读:
    DataTable常用操作总结[转帖]
    Jquery实现淡入淡出效果
    在自定义Server Control中捆绑JS文件 [转帖]
    ASP.NET利用String.Join以分隔符號來串連集合資料 [转帖]
    fork()的一些测试
    大端小端表示法 && GAS对过程的实现
    GAS中流程控制的实现,for, while, if, switch
    一个看起来奇怪的C++程序 && c++操作符重载
    修改函数的返回地址
    stl algorithm sort ,unique
  • 原文地址:https://www.cnblogs.com/suika/p/8534226.html
Copyright © 2011-2022 走看看