题目地址
题面
样例输入
4
1 1 1 1
1 1 1 1
1 1 1 1
1 1 1 1
样例输出
2
样例输入
4
1 0 1 1
1 1 1 1
1 1 1 1
1 1 1 1
##样例输出
0
思路
先用n皇后的方法放黑棋,当黑棋放完之后再放白棋。
AC代码:
#include <iostream>
using namespace std;
const int N = 20;
int n;
int res; // 放结果
int g[N][N];
bool colb[N], dgb[N], udgb[N];
bool colw[N], dgw[N], udgw[N];
void dfs_white(int u)
{
if (u == n) // 如果白皇后也放完,可行结果加一
{
res++;
return;
}
for (int i = 0; i < n; i++)
{
if (g[u][i] == 1 && !colw[i] && !dgw[u + i] && !udgw[u - i + n])
{
g[u][i] = 3;
colw[i] = dgw[u + i] = udgw[u - i + n] = true;
dfs_white(u + 1);
colw[i] = dgw[u + i] = udgw[u - i + n] = false;
g[u][i] = 1;
}
}
}
void dfs_black(int u) // 第u行
{
if (u == n)
{
dfs_white(0); // 黑皇后放完,开始放白皇后
}
for (int i = 0; i < n; i++)
{
if (g[u][i] == 1 && !colb[i] && !dgb[u + i] && !udgb[u - i + n])
{
g[u][i] = 2;
colb[i] = dgb[u + i] = udgb[u - i + n] = true;
dfs_black(u + 1);
colb[i] = dgb[u + i] = udgb[u - i + n] = false;
g[u][i] = 1;
}
}
}
int main()
{
cin >> n;
for (int i = 0; i < n; i++)
for (int j = 0; j < n; j++)
cin >> g[i][j];
// 先放黑皇后,再放白皇后
dfs_black(0); // 第0行开始枚举黑皇后
cout << res << endl;
return 0;
}