HDU 2553 N皇后问题 (回溯法 递归·非递归)
来源:互联网 发布:蔡健雅 知乎 编辑:程序博客网 时间:2024/05/22 00:19
题意 中文n*n的棋盘放n个皇后(攻击同行/列/主副对角线) 使任何两个都不互相攻击 有多少种方法
枚举每一行 用vis[3][i]记录列 主对角线 副对角线是否被占 同列和对角线都没被占就继续枚举下一行 当枚举到n+1行的时候就是一个合法答案了
注: n*n的方阵中主对角线可以用(i-j+n)标号 副对角线可以用(i+j)标号
//ans[]={0,1,0,0,2,10,4,40,92,352,724};#include<cstdio>#include<cstring>using namespace std;const int N = 50;int n, cnt, vis[3][N], ans[N];void getans(int cur){ if(cur == n) ++cnt; for(int i = 0; cur < n && i < n; ++i) { if(vis[0][i] || vis[1][cur + i] || vis[2][cur - i + n]) continue; vis[0][i] = vis[1][cur + i] = vis[2][cur - i + n] = 1; getans(cur + 1); vis[0][i] = vis[1][cur + i] = vis[2][cur - i + n] = 0; }}int main(){ for(int i=1;i<=10;++i) { cnt = 0,n=i; getans(0); ans[i]=cnt; } while(scanf("%d", &n), n) printf("%d\n", ans[n]); return 0;}
非递归的回溯
#include <cstdio>#include <cmath>using namespace std;const int M = 20, N = 8;int col[M], vis[3][M], last[M], cnt;bool check(int r) //判断前r行是否有冲突{ for(int i = 1; i < r; ++i) //主i + col[i] == r + col[r], 副i - col[i] == r - col[r] if(i + col[i] == r + col[r] || i - col[i] == r - col[r] || col[i] == col[r]) return false; return true;}void gao(){ int r = 1; col[1] = 0; while(r) { col[r] = col[r] + 1; //第r行的皇后换新位置 if(col[r] > N) {--r; continue;} if(!check(r)) continue; if(r == N) { for(int i = 1; i <= N; ++i) printf("%d ", col[i]); puts(""); ++cnt; } else col[++r] = 0; }}int main(){ cnt = 0; gao(); printf("%d\n", cnt); return 0;}
还有可以打印答案的
#include<cstdio>#include<cstring>using namespace std;const int N = 1000;int n, cnt, c[N], col[N][N], vis[3][N];void getans(int cur){ if(cur == n) { ++cnt; for(int i = 0; i < n; ++i) col[cnt][i] = c[i]; } else { for(int i = 0; i < n; ++i) if(!vis[0][i] && !vis[1][cur + i] && !vis[2][cur - i + n]) { c[cur] = i; vis[0][i] = vis[1][cur + i] = vis[2][cur - i + n] = 1; getans(cur + 1); vis[0][i] = vis[1][cur + i] = vis[2][cur - i + n] = 0; } }}int main(){ while(scanf("%d", &n)) { memset(vis, 0, sizeof(vis)); cnt = 0; getans(0); printf("%d皇后问题共有%d组解:\n\n", n, cnt); for(int k = 1; k <= cnt; ++k) { for(int i = 0; i < n; ++i) { for(int j = 0; j < n; ++j) printf("%d ", j == col[k][i]); printf("\n"); } printf("\n"); } } return 0;}
N皇后问题
Problem Description
在N*N的方格棋盘放置了N个皇后,使得它们不相互攻击(即任意2个皇后不允许处在同一排,同一列,也不允许处在与棋盘边框成45角的斜线上。
你的任务是,对于给定的N,求出有多少种合法的放置方法。
你的任务是,对于给定的N,求出有多少种合法的放置方法。
Input
共有若干行,每行一个正整数N≤10,表示棋盘和皇后的数量;如果N=0,表示结束。
Output
共有若干行,每行一个正整数,表示对应输入行的皇后的不同放置数量。
Sample Input
1850
Sample Output
19210
1 0
- HDU 2553 N皇后问题 (回溯法 递归·非递归)
- n皇后问题【非递归回溯】
- N皇后问题的非递归回溯和递归回溯
- 非递归求解N皇后问题(回溯法)
- HDOJ/HDU 2553 N皇后问题 回溯加递归
- N皇后问题 HDU 杭电2553【递归回溯】
- n皇后问题--递归回溯
- N皇后问题递归回溯
- 回溯法解决N皇后问题——递归与非递归求解
- 非递归回溯算法求解n-皇后问题
- 用栈+回溯+非递归解决N皇后问题
- 八皇后问题(回溯+递归)/(回溯+非递归)
- 八皇后问题 回溯 非递归 java
- N皇后问题的递归回溯实现
- N皇后问题(回溯递归)
- N皇后问题 --递归及回溯解决方案
- 回溯法-5.5.1 n皇后问题之递归法
- 递归实现回溯法求n皇后问题
- path的使用
- SKIP_BODY,SKIP_PAGE,EVAL_BODY_INCLUDE,EVAL_BODY_AGAIN
- 排序算法之冒泡排序 C++和PHP实现
- make: warning: Clock skew detected. Your build may be incomplete.
- ppt转换成pdf转换器怎么使用
- HDU 2553 N皇后问题 (回溯法 递归·非递归)
- 使用标准库函数中的printf
- 关于Activity的面试
- java.lang.UnsupportedOperationException
- c# socket 判断端口是否被占用
- android 对话框总结
- ASCII、Unicode、GBK和UTF-8字符编码的区别联系
- 内置传感器---智能手机(资料)
- Java学习的30个目标以及系统架构师推荐的书