zoukankan      html  css  js  c++  java
  • codeforces 486B.OR in Matrix 解题报告

    题目链接:http://codeforces.com/problemset/problem/486/B

    题目意思:给出一个m行n列的矩阵B(每个元素只由0/1组成),问是否可以利用矩阵B,通过一定的运算逆回来求出矩阵A(行和列数都跟B相同)。可以的话输出"YES" 并输出矩阵A,否则输出 "NO"。运算如下:

        

         也就是,Bij 是通过 A 矩阵第 i 行中所有的数做 或(|) 运算接着再跟所有第 j 列中所有的数做 或 运算求出来的。or 运算就是除了所有元素都为 0 的情况,or出来的结果为0外,其他情况算出来都是1(至少有一个元素是 1 即可)。

        以下注释部分可以忽略~~~

        /******************************************

         我一开始的错误做法是利用两个数组 row[] 和 col[] ,初始化使得row[1]~row[m] 都为1,col[1]~col[n] 都为1。当 Bij = 0 时,令 row[i] = 0,col[j] = 0来表示第 i 行 和 第 j 列都必须要填 0。这样才能保证 or 出来的结果是0嘛~~然后找出矛盾,即如果b[i][j] = 0,它需要满足row[i] == 0 且 col[j] == 0;如果b[i][j] = 1,但遇到row[i] == 0 且 col[j] == 0,那么就表示有矛盾啦。最后就根据如果row[i] == 0 或者 col[j] == 0 就输出0,否则输出1。

        不过仔细想一下,其实填1的情况是比较复杂的,例如b[i][j] = 1,那么并不能确定究竟是因为row[i] = 1 还是 col [j] = 1,而输出如果仅仅是根据 row[i] == 0 或者 col[j] == 0 输出0是不对的,试想,因为只要保证其中一个(row[i] == 0 && col[j] == 1类似这种)是1即有可能输出1了。于是最终测试遇到这组数据的时候就呵呵了~~~(我的输出是9个0,明显是错的)

         1  0 0

         1  0 0     

        1  0 0

       如果按我的做法,那么分析结果是row[1] = 0, row[2] = 0, row[3] = 0,col[1] = 1,col[2] = 0,col[3] = 0。b[i][j] == 1 且 row[i] == 0 && col[j] == 0 是得不出矛盾的。例如b[1][1] = 1,它只是row[1] = 0,但col[1] != 0。

    ************************************************/

        正确的做法要用到逆向思维。首先根据b[i][j]构造出相应的a[i][j] 哪些数必定为1。如果b[i][j] = 0,那么a[i][0]~a[i][n-1] 都为0,a[0][j]~a[m-1][j] 都为0。那么逆回来就是如果a[i][j] = 1,那么b[i][0]~b[i][n-1]所有元素都为1,b[0][j] ~b[m-1][j]所有元素都为1,就是没有一个元素等于0!是不是很神奇呢~~~~然后利用矩阵a求出对应的b'[i][j](代码中是c[i][j]),然后对比b[i][j]是否跟c[i][j]不同,不同即引出矛盾。

          这种思维确实需要好好锻炼!!!

     1 #include <iostream>
     2 #include <cstdio>
     3 #include <cstdlib>
     4 #include <cstring>
     5 using namespace std;
     6 
     7 const int maxn = 100 + 10;
     8 int a[maxn][maxn], b[maxn][maxn];
     9 int c[maxn][maxn];
    10 
    11 int main()
    12 {
    13     int m, n;
    14     while (scanf("%d%d", &m, &n) != EOF)
    15     {
    16         for (int i = 0; i < m; i++)
    17         {
    18             for (int j = 0; j < n; j++)
    19                 scanf("%d", &b[i][j]);
    20         }
    21         memset(a, 0, sizeof(a));
    22         for (int i = 0; i < m; i++)   // 构造a矩阵
    23         {
    24             for (int j = 0; j < n; j++)
    25             {
    26                 bool ok = false;
    27                 for (int l = 0; l < m; l++)  //
    28                 {
    29                     if (!b[l][j])          
    30                         ok = true;
    31                 }
    32                 for (int l = 0; l < n; l++)  //
    33                 {
    34                     if (!b[i][l])
    35                         ok = true;
    36                 }
    37                 if (!ok)          // a[i][j] 填1必须要满足b[0][j]~b[m-1][j]以及b[i][0]~b[i][n-1]没有一个元素等于0。
    38                     a[i][j] = 1;
    39             }
    40         }
    41         // 从a矩阵经计算应该得到的b矩阵
    42         for (int i = 0; i < m; i++)
    43         {
    44             for (int j = 0; j < n; j++)
    45             {
    46                 if (a[i][j] == 1)
    47                 {
    48                     for (int l = 0; l < m; l++)
    49                         c[l][j] = 1;
    50                     for (int l = 0; l < n; l++)
    51                         c[i][l] = 1;
    52                 }
    53             }
    54         }
    55         // 检查是否有矛盾
    56         bool ok = true;
    57         for (int i = 0; i < m && ok; i++)
    58         {
    59             for (int j = 0; j < n && ok; j++)
    60             {
    61                 if (c[i][j] != b[i][j])
    62                 {
    63                     ok = false;
    64                     break;
    65                 }
    66             }
    67         }
    68         printf("%s
    ", ok ? "YES" : "NO");
    69         for (int i = 0; i < m && ok; i++)
    70         {
    71             for (int j = 0; j < n; j++)
    72                 cout << a[i][j] << (j == n-1 ?  "
    " : " ");
    73         }
    74     }
    75     return 0;
    76 }
  • 相关阅读:
    使用express框架创建服务器
    搭建第一个node服务器
    Node 与JS的区别
    node学习之路
    【每天一个linux命令】read
    【每天一个linux命令】awk
    【每天一个linux命令】wc
    【每天一个linux命令】sed
    【每天一个linux命令】tee
    【每天一个linux命令】find
  • 原文地址:https://www.cnblogs.com/windysai/p/4092508.html
Copyright © 2011-2022 走看看