「这是我参与2022首次更文挑战的第23天,活动详情查看:2022首次更文挑战」
💛作者主页:静Yu
🧡简介:CSDN全栈优质创作者、华为云享专家、前端知识交流社区创建者
💛社区地址:bbs.csdn.net/forums/Jing…
第十三届蓝桥杯大赛个人赛省赛比赛将于2022年4月9日(星期六)举办,趁现在寒假的时间抓紧时间备战一下。因为博主本人报名是C/C++组,所以更新所有内容都是C/C++相关知识。题目全部都是蓝桥杯官网题库真题。今天是备战刷题的第十六天。 题目: 给定一个n*n的棋盘,棋盘中有一些位置不能放皇后。现在要向棋盘中放入n个黑皇后和n个白皇后,使任意的两个黑皇后都不在同一行、同一列或同一条对角线上,任意的两个白皇后都不在同一行、同一列或同一条对角线上。问总共有多少种放法?n小于等于8。
输入格式:
输入的第一行为一个整数n,表示棋盘的大小。 接下来n行,每行n个0或1的整数,如果一个整数为1,表示对应的位置可以放皇后,如果一个整数为0,表示对应的位置不可以放皇后。
输出格式:
输出一个整数,表示总共有多少种放法。
样例输入:
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皇后,再用同样的方式求解出2n皇后。题目给出了黑白皇后,顺序不重要,先放黑的话就在放白皇后,先放白的就再放黑的。主函数非常简单就是输入第一行数和循环输入下边的矩阵。最主要的内容就是皇后的位置判断,同行同列不能有重复的数字,如果同斜线,行号-列号之差绝对值相等说明在同一条对角线上。按照这种思路完成代码即可。 完整代码:
#include<iostream>
using namespace std;
int sum=0,n;
int a[10][10];
void huanghou(int i,int m){
for(int j=0;j<n;j++){
if(a[i][j]!=1){ //只要是不为1,其他数字都不能添加皇后,直接跳出
continue;
}
int x=j-1,y=j+1,z=1,k;
for(k=i-1;k>=0;k--){
if(a[k][j]==m || x>=0 && a[k][x]==m || y<n && a[k][y]==m){
z=0; //本题从上往下遍历,同一行的可以不用检测,还没有到达的行也不用检测,只需要检测同一列和左右上角就行
break;
} //如果出现皇后则不符题意,直接跳出,不执行下述步骤
x--;y++;
}
if(z){
a[i][j]=m;
if(i!=(n-1)){
huanghou(i+1,m); //矩阵从零开始存储数据,当i=n-1时说明黑皇后已经放完,可以放白皇后了
}
else{
if(m==2){
huanghou(0,3);
}
else{
sum++; //当白皇后放完则表示一种放法
}
}
a[i][j]=1; //完成之后恢复原来的值,继续检测
}
}
}
int main(){
cin>>n;
for(int i=0;i<n;i++){
for(int j=0;j<n;j++){
cin>>a[i][j]; //输入矩阵
}
}
huanghou(0,2); //2代表黑棋,3代表白棋
cout<<sum;
}