题解 AT47 【パズルのお手伝い】

传送门

题意:

很经典的八皇后问题,已知三个皇后的位置,求剩下五个皇后的位置,如果无解输出“\(No Answer\)

思路:

很显然dfs可以解决,暴力枚举每一行放的位置,通过已经放过的皇后的位置可以判断出很多不合法的位置,加上该剪枝即可

代码实现:

#include <cstdio>
#include <algorithm>
#include <cstring>
#include <iostream>
using namespace std;
inline int read () {
	int x = 0, f = 1; char ch = getchar();
	for (;!isdigit(ch); ch = getchar()) if (ch == '-') f = -1;
	for (; isdigit(ch); ch = getchar()) x = x * 10 + ch - '0';
	return x * f;
}
const int maxn = 10;
int choose[maxn][maxn];
int ans[maxn][maxn];
int col[maxn];
void updata (int x, int y) {
	for (int k = 1; k <= 8; k++) choose[x][k]++, choose[k][y]++;
	for (int k = 1; k + x <= 8 && k + y <= 8; k++) choose[x + k][y + k]++;
	for (int k = 1; x - k >= 1 && y - k >= 1; k++) choose[x - k][y - k]++;
	for (int k = 1; x - k >= 1 && y + k <= 8; k++) choose[x - k][y + k]++;
	for (int k = 1; x + k <= 8 && y - k >= 1; k++) choose[x + k][y - k]++;
	choose[x][y]--;
}
void Delete (int x, int y) {
	for (int k = 1; k <= 8; k++) choose[x][k]--, choose[k][y]--;
	for (int k = 1; k + x <= 8 && k + y <= 8; k++) choose[x + k][y + k]--;
	for (int k = 1; x - k >= 1 && y - k >= 1; k++) choose[x - k][y - k]--;
	for (int k = 1; x - k >= 1 && y + k <= 8; k++) choose[x - k][y + k]--;
	for (int k = 1; x + k <= 8 && y - k >= 1; k++) choose[x + k][y - k]--;
	choose[x][y]++;
}
bool judge = false;
void dfs (int num) {
	if (num == 9) {
		judge = true;
		return;
	}
	if (col[num]) dfs (num + 1);
	if (judge == true) return;
	for (int i = 1; i <= 8; i++) {
		if (choose[num][i]) continue;
		ans[num][i] = 1;
		updata (num, i);
		dfs (num + 1);
		if (judge == true) return;
		ans[num][i] = 0;
		Delete (num, i);
	}
	if (judge == true) return;
}
int main () {
	char c;
	for (int i = 1; i <= 8; i++) {
		for (int j = 1; j <= 8; j++) {
			scanf (" %c", &c);
			if (c == 'Q') {
				if (choose[i][j] != 0) return puts("No Answer"), 0;
				ans[i][j] = 1;
				col[i] = 1;
				updata (i, j);
			}
		}
	}
	dfs (1);
	if (judge == true) {
		for (int i = 1; i <= 8; i++) {
			for (int j = 1; j <= 8; j++) {
				if (ans[i][j] == 1) printf ("Q");
				else printf (".");
			}
			puts("");
		}
	} else {
		puts("No Answer");
	}
	return 0;
}

posted @ 2020-11-23 20:23  Blancа  阅读(118)  评论(1编辑  收藏  举报
哈哈,你打开了控制台,是想要看看我的秘密吗?
莫挨老子!