<-求赞
宣传博客!
题目链接
代码里有详细注释
#include <bits/stdc++.h>
using namespace std;
#define int long long
int b[110][110],a[110][110]; // a 、 b 含义均同题目
signed main()
{
int n,m; // 以我们平时的认知, n 为行数, m 为列数,而题目中似乎是反过来的,我也不习惯按题目里的写,就按平时的认知写了,别搞混了
cin >> n >> m;
for(int i = 1; i <= n; i++)
{
for(int j = 1; j <= m; j++)
a[i][j] = 1; // “往好的想”,先假设 a 数组里全是 1
}
for(int i = 1; i <= n; i++)
{
for(int j = 1; j <= m; j++)
{
cin >> b[i][j];
if(b[i][j] == 0) // 当 b[i][j] = 0 时,条件比较严,在输入时就根据它来修改 a 数组,我们视它为“一个炸弹”
{
for(int xpos = 1; xpos <= n; xpos++) // 对于这个“炸弹”所在的一列,都被“炸”成了 0
a[xpos][j] = 0;
for(int ypos = 1; ypos <= m; ypos++) // 对于这个“炸弹”所在的一行,也都被“炸”成了 0
a[i][ypos] = 0;
}
}
}
bool possible = true; // possible 表示:是否可行
for(int i = 1; i <= n; i++)
{
for(int j = 1; j <= m; j++)
{
if(b[i][j] == 0) // b[i][j] = 0,也就是它是“炸弹”的时候,已经考虑过了,现在就不用管了,我们只考虑 b[i][j] = 1 的时候
continue;
int cnt = 0; // 统计 (i,j) 所在的行、列里 a 数组为 1 的个数
for(int xpos = 1; xpos <= n; xpos++) // 遍历它所在的一列
cnt += a[xpos][j]; // 为什么能直接加 a[i][j] 呢?因为当 a[i][j] = 0 时,加了等于没加,而当它等于一时, cnt 也正好会加 1
for(int ypos = 1; ypos <= n; ypos++) // 遍历它所在的一行
cnt += a[i][ypos];
if(cnt == 0) // 当 b[i][j] = 1 时,如果它所在的行和列里没有一个一,不符合题意,所以是不能构造出 a 数组的
{
possible = false; // 把可行标志设为 false
break; // 都不可行了还继续循环干嘛,停了!
}
}
}
// 以下均为输出
if(!possible)
cout << "NO" << "\n";
else
{
cout << "YES" << "\n";
for(int i = 1; i <= n; i++)
{
for(int j = 1; j <= m; j++)
cout << a[i][j] << " ";
cout << "\n";
}
}
return 不要复制粘贴我的代码哦~;
}
or