仔细思考深度优先搜索其实可以分为大概四步.
1.发现,找到想要找的节点,如八皇后就是找到当前行放置皇后的那个点,马走日就是下一步的落点.
2.递进,如果不满足结束条件就继续递归,进入下一层.如八皇后问题就是进入下一行.
3.满足,条件满足了之后,就输出结果,一般都是用一个全局变量来控制数量,一旦==N,就输出结果.
4.返回,dfs得回溯才能遍历所有的结果.
问题描述
八皇后问题是一个以国际象棋为背景的问题:如何能够在8×8 的国际象棋棋盘上放置八个皇后,使得任何一个皇后都无法直接吃掉其他的皇后?
也就是说,使得棋盘中每个横向、纵向、左上至右下斜向、右上至左下斜向均只有一枚皇后。
代码如下:
#include"stdio.h"
#include"math.h"
const int N = 8;
int a[N] = {0};
int solution = 0;
bool isok(int row,int col)//判断这个位置是否可以放置皇后
{
for (int i = 0; i < row; i++)
{
//a[i]的值代表着列,i代表着行,所以重0开始遍历验证行和列有没有重复的
if(a[i] == col || abs(a[i] - col) == row - i)
{
return false;
}
}
}
void Display()//如果数组中个数到达了N个则输出,相当于dfs的结束条件
{
printf("第%d种解: \n",++soulution);
for (int i = 0; i < N; i++)
{
for (int j = 0; j < N; j++)
{
if (a[i] == j)
{
printf("%d",i);
}
else
{
printf("#");
}
}
printf("\n");
}
printf("---------------------\n");
}
/*
从0,0这个位置开始循环,因为注定每一行都会有一个皇后,所以在第0行就有8种放法,之后依次下移.
相当于递归,结束条件就是row=N-1,也就是每一行都放了一个皇后,相当于一种解法.
*/
void DFS(int row)
{
for(int col = 0;col < N;col++)
{
if (isok(row,col))
{
a[row] = col;
if (row != N-1)
{
DFS(row + 1);
}
else
{
Display();
}
}
}
}
int main()
{
DFS(0);
return 0;
}