|
采用类似pmn的做法,因为每航只有一个皇后,所以我们设第i行的皇后摆在a(i)位置,那么如何选择a(i)就可以用dfs法,于是得到代码
- #include <iostream>
- using namespace std;
- int s=0,a[10];
- bool canp(int i,int k) ///第i行能否放在k位置
- {
- bool b=1;
- return 1; ///这里先不写
- }
- void pr()
- {
- cout<<endl<<++s<<':';
- for (int i=1; i<=8; i++) cout<<a[i]<<' ';
- }
- void dfs(int i)
- {
- if (i>8) pr();
- else
- for (int k=1; k<=8; k++)
- if (canp(i,k))
- {
- a[i]=k;
- dfs(i+1);
- }
- }
- int main()
- {
- dfs(1);
- return 0;
- }
复制代码
中间canp函数用来判断第i行能否放在k位置上,先不写,检测下主函数是否正确,得到好多解,答案有问题但是思路是对的。
现在在canp里面加入一句,判断这一列是否有冲突的语句,这个简单,主要前面i-1行中某一个a(i)==k就表明有冲突
- bool canp(int i,int k) ///第i行能否放在k位置
- {
- bool b=1;
- for (int j=1; j<=i-1; j++)
- if (a[j]==k) b=0;
- return b;
- }
复制代码
加上后运行,答案少了很多,说明是有效的判断,然后再思考如何加上对角线的限制,看图
javascript:;
我们找到规律 同对角线的i+a(i)的值是一样的,反对角线的i-a(i)的值是一样的,那么再加上这两个判断
- bool canp(int i,int k) ///第i行能否放在k位置
- {
- bool b=1;
- for (int j=1; j<=i-1; j++)
- if (a[j]==k) b=0;
- for (int j=1; j<=i-1; j++)
- if (a[j]+j==k+i) b=0;
- for (int j=1; j<=i-1; j++)
- if (j-a[j]==i-k) b=0;
- return b;
- }
复制代码
程序答案就是92种解 |
本帖子中包含更多资源
您需要 登录 才可以下载或查看,没有帐号?立即注册
x
|