题目描述
N皇后问题研究的是如何将
n
个皇后放置在n×n
的棋盘上,并且使皇后彼此之间不能相互攻击。如果两个皇后在同一行或者同一列或者同一斜线上,那么它们可以互相攻击,否者不能互相攻击。返回所有不同的n
皇后问题的解决方案的数量。
输入格式
数字
n
表示皇后的数量。输出格式
一个数字。
输入输出样例
输入
8
输出
92
解释 符合题目要求的不重复的解决方案总共有
92
种。
思路:回溯算法的思路符合我们正常思考的模式,即在每次放置皇后时,判断此时这一行放置的皇后与之前行的皇后是否符合不能相互攻击的要求。如果符合要求,那么将皇后放置;如果不符合要求,说明该位置不合适,判断这一行下一个放置位置。
#include<bits/stdc++.h>
using namespace std;
int sum=0;//计数
int row=0;//行
int line[100]={0};//存储放置好的皇后的列数
bool Judge(int row)
{
int j=0;
while(j<row)//第三个循环,判断第row行放置的皇后是否符合要求
{
if(line[row]==line[j]||(abs(row-j)==abs(line[row]-line[j])))
//line[row]依次与0到row-1行的line,判断是否有位于同一列的皇后
//(abs(row-j)==abs(line[row]-line[j]):判断是否有斜线上的皇后(行间距和列间距相等,那么两皇后在斜线上)
return false;
j++;
}
return true;
}
void Process(int *flag,int n,int row)
{
if(row==n)
{
sum++;
return ;
}
for(int i=0;i<n;i++)//第二个循环,在每一行中寻找所有符合的皇后位置
{
if(flag[i]==0)
{
line[row]=i;
if(Judge(row)){
flag[i]=1;
Process(flag,n,row+1);
flag[i]=0;
}
else{
continue ;
}
}
}
}
int main()
{
int n;
cin>>n;
int flag[10]={0};
for(int i=0;i<n;i++)//第一个循环,按行放置皇后
{
if(flag[i]==0)
{
flag[i]=1;
line[row]=i;
Process(flag,n,row+1);
flag[i]=0;
}
}
cout<<sum;
}
回溯条件:放置皇后的位置与其他皇后在同一行或者同一列或者同一斜线上,会彼此攻击,于是进行回溯。
一轮皇后位置判断结束条件:N行都放置好了皇后,并且不冲突。