B-Mine Sweeper II

2020 ICPC Shanghai Station B
link to the original question: https://ac.nowcoder.com/acm/contest/10330/B The
Insert picture description here
Insert picture description here
Insert picture description here
question is intended
to give you two minesweeping plans A and B of size n * m, and it is required to pass at most n * m /2 conversions (conversion refers to turning a grid that is not a mine into a mine, or turning a grid that is a mine into a blank grid), so that the value of the B picture is equal to the value of the A picture (the value refers to all the minesweeping pictures The sum of numbers, where there are no numbers or thunder, the value is 0)

Ideas
In fact, for this question, as long as one thing is connected, it is enough.
(The effect of a mine on the blank squares around him) is equivalent to (the effect of turning all the blank squares around him into mines and turning themselves into blank squares), that is, this reverses the picture ( Thunder becomes blank, blank becomes thunder), which is actually the same as the original picture. And the title says that at most mn/2 conversion operations can be performed, then B picture must be converted into A picture or the inverse of A (this should be called a complement picture), that is, there is no -1 situation, so as long as Find out the complementary picture, and then see which of A or A’s complementary picture is converted into B with less than nm/2. That picture will do. It may not be very clear. Forgive me

AC code

#include <bits/stdc++.h>
using namespace std;
#define maxn 1005

char G[maxn][maxn];// 图A
char G2[maxn][maxn];// 图A 的 补图
char K[maxn][maxn];// 图B
int n, m;

int main(){
    
    
	scanf("%d %d", &n, &m);
	for(int i=1;i<=n;++i) scanf("%s", G[i]+1);
	for(int i=1;i<=n;++i) scanf("%s", K[i]+1);
	for(int i=1;i<=n;++i)
		for(int j=1;j<=m;++j)
			G2[i][j]=(G[i][j]=='.'?'X':'.'); // 求图A 的 补图
	int cnt=0, cnt2=0; //分别用来记录 把图A 转换 成图B 和 把图A的补图 转换成B 所需的转换次数
	for(int i=1;i<=n;++i)
		for(int j=1;j<=m;++j)
			if(G[i][j]^K[i][j]) cnt++;
	for(int i=1;i<=n;++i)
		for(int j=1;j<=m;++j)
			if(G2[i][j]^K[i][j]) cnt2++;
	if(cnt<=n*m/2){
    
    //只要 转换次数符合条件 就输出
		for(int i=1;i<=n;++i) printf("%s\n", G[i]+1);
	}
	else{
    
    
		for(int i=1;i<=n;++i) printf("%s\n", G2[i]+1);
	}

	return 0;
}```

Guess you like

Origin blog.csdn.net/qq_45757639/article/details/111395644
ii