八皇后非递归回溯算法c语言,[回溯法]八皇后问题的递归与非递归算法

八皇后的问题非常有名,初次理解可能稍有难度,不过多看书,看博客和代码,几遍下来,也基本清晰。

首先不用想初始的情况,先假设前面已经排列好了几个皇后,即将排列下一个皇后。依次遍历八个位置,然后与之前的进行判断这个位置是否可行,如可行则进行下一个皇后,否则则移动位置继续判断。很简单。但是有两个个问题:

1、不全,某个位置有八种方法排列,你只用了一种,当然你可以每个位置遍历,但太耗时,回溯法可以解决很大的一部分问题,即当你在对某一行皇后进行放置时,如果一直放不好(到最后),那后面的行就不需要再遍历了,直接回溯上一行,将上一行的位置后移——依次进行这个步骤,直到第一行,遍历结束。

2、如何判定当前位置合法?首先,两个皇后不能同一列(这里要注意,算法的遍历次序是按行来的,所以不必考虑行的情况),其次,不能斜对角。

代码如下,很清晰:

#define N 8

/* Place(),第一个参数表示八皇后的列位置,第二个表示当前要插入的八皇后的行数。 */

bool Place(int eightqueen[],int k)

{

int i = 0;

while(i

{

if(eightqueen[i] == eightqueen[k] || abs(eightqueen[i] - eightqueen[k]) == abs(i- k))

{

return false;

}

i++;

}

return true;

}

行是从0开始,而列是从1开始。

1、递归解法

int eight_queen[N] = {0};

int gcount = 0;

void Eight_Queen_Recursion(int eight_queen[],int i)

{

eight_queen[i]++;

while(!Place(eight_queen,i) && eight_queen[i]<=N)

{

eight_queen[i] ++;

}

if(eight_queen[i] <= N)

{

if(i == N -1 )

{

gcount ++;

}

else

{

i++;

eight_queen[i] = 0;

}

Eight_Queen_Recursion(eight_queen,i);

}

else

{

i--;

if(i<0)

{

return;

}

Eight_Queen_Recursion(eight_queen,i);

}

}

void main()

{

Eight_Queen_Recursion(eight_queen,0);

cout<

}

2、非递归解法

void Eight_Queen()

{

int eight_queen[N] = {0}; //初始化八皇后的列。每一行的八皇后所在的列

int i = 0;

int count = 0;

while(i>=0)

{

eight_queen[i]++; //从1开始

while(!Place(eight_queen,i) && eight_queen[i] <= N) //判断此列是否符合条件。

{

eight_queen[i] ++; //将列位置后移

}

if(eight_queen[i] <= N)

{

//找到一个位置

if(i == N-1)

{

//这是一个解

count ++;

}

else

{

//没有到最后一行,则进行下一行

i++;

eight_queen[i] = 0; //下一列从0开始

}

}

else//如果这一行到最后也没有找到合适的列,则回溯上一行。

{

i--;

}

}

cout<

}

void main()

{

Eight_Queen();

}

将Place函数与下面的结合,即是完整的程序。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值