八皇后问题——深度优先搜索和回溯

/*P1219 八皇后
题目描述
检查一个如下的6 x 6的跳棋棋盘,有六个棋子被放置在棋盘上,使得每行、每列有且只有一个,每条对角线(包括两条主对角线的所有平行线)上至多有一个棋子。
这只是跳棋放置的一个解。请编一个程序找出所有跳棋放置的解。并把它们以上面的序列方法输出。解按字典顺序排列。请输出前3个解。最后一行是解的总个数。

输入输出格式
输入格式:
一个数字N (6 <= N <= 13) 表示棋盘是N x N大小的。
输出格式:
前三行为前三个解,每个解的两个数字之间用一个空格隔开。第四行只有一个数字,表示解的总数。
输入输出样例
输入样例#1: 
6
输出样例#1: 
2 4 6 1 3 5
3 6 2 5 1 4
4 1 5 2 6 3
4*/
#include<iostream>
using namespace std;
int a[50], b[50], c[50], d[50]; //四个一维数组记录行列两个对角线
int n, res;
void dfs(int i)
{
if (i > n)      //i>n是我们的递归出口
{
res++;
if (res > 3)                      //只输出前三个,多的就不输出了
return;
else
{
for (int k = 1; k <= n; k++)
cout << a[k] << ' ';
cout << endl;
}
}
for (int j = 1; j <= n; j++)                  //从第一列开始,一个个循环枚举下去
{
    if (!b[j] && !c[i + j] && !d[i - j + n])  //左下到右上的各个对角线中每个格子的行号加列号都相同!故c[i+j]表示一 条对角线                      //同理右下到左上各个对角线中每个格子的行号减列号都相同,以为不能为负,故d[i-j+n],加个n偏移量不会影响!
{ a[i] = j;   //皇后在第I行J列
b[j] = 1;             //占领范围标记为1
c[i + j] = 1;
d[i - j + n] = 1;
dfs(i + 1);       //找下个皇后
a[i] = 0;         //注意要还原回溯,才能重复使用!!
b[j] = 0;
c[i + j] = 0;
d[i - j + n] = 0;
}
}
}
int main()
{
cin >> n;
dfs(1);                //从第一个皇后第一行开始,以后都是第I行第I个皇后
cout << res;
return 0;
}
展开阅读全文

没有更多推荐了,返回首页