LeetCode OJ - N-Queens 回溯法
2014-04-27 19:30
447 查看
寻找问题解的一个方法,可以采用列出所有候选解,检查完所有候选解即可得到需要的解。
问题:其中的问题在于,候选解数量很庞大时,采用遍历搜索耗费的时间巨大。
解决:采用不同的筛选方法,减小问题的规模,从而缩短搜索的时间。
方法:回溯法、分支界定法
——————————————————————————————————————————
回溯算法 http://blog.csdn.net/pinkrobin/article/details/5378702
The n-queens puzzle is the problem of placing n queens on an n×n chessboard such that no two queens attack each other.
Given an integer n, return all distinct solutions to the n-queens puzzle.
Each solution contains a distinct board configuration of the n-queens' placement, where
indicate a queen and an empty space respectively.
For example,
There exist two distinct solutions to the 4-queens puzzle:
思考:
1.总体思路
2.采用什么数据结构
3.需要解决的问题
4.采用什么程序结构
假设棋盘式NxN的二维数组,首先在第一行放置一个Q,接着在第二行放,直到放到第N行,若放置完成则表示找到一种解决方案。如何遍历所有解决方案呢,可以采用递归的方式,使用深度遍历找出所有方案(调用Q(0))。
应该采用什么数据结构呢,若采用二维数组Q
,需要解决A.该行是否有元素 B.该列是否有元素 C.该对角线上是否有元素,这几个应该好解决。若现在要在(row, col)这个点上检查是否可以放皇后,row行没还没放故只用判断row行之前的情况,判断如下:
bool flag = false; //不能放置皇后
for(i = row-1; i >= 1; i--) {
//每行应该判断三个点:Q[i][col+i-row]、 Q[i][col]、 Q[i][col-i+row]
// 可通过判断行列的变化情况找到这三个点
if( Q[i][col+i-row] == 0 && Q[i][col] == 0 && Q[i][col-i+row] ) {
flag = true;
Q[row][col] = 1;
}
}
如果要记录下所有结果呢,也就是所有的二维表结果,应该怎么设计呢? 因为深度遍历每一次从根节点,访问到叶子节点,本身就是一种解决方案,记录该方案即可。采用输出表示记录该方案。
bool isPutQueen(int row, int col) {
bool flag = false;
for(int i = row - 1; i >= 1; i--) {
if(!Q[i][col+i-row] && !Q[i][col] && !Q[i][col-i+row]) {
flag = true;
break;
}
}
return flag;
}
void NQueen(int row) {
if(row == N) {
for(int i = 1; i <= N; i++) {
for(int j = 1; j <= N; j++) {
cout << Q[i][j] << " ";
Q[i][j] = 0;
}
cout << endl;
}
cout << endl;
return ;
} else {
for(int i = 1; i <= N; i++) {
for(int j = 1; j <= N; j++)//回溯法的精髓,记录了前面row-1行的情况
Q[row][j] = 0;
if(isPutQueen(row, i)) {
NQueen(row++);
}
}
}
}
#define N 16
int Q[N + 1][N + 1];
int main() {
InitQueen();
NQueen(1);
return 0;
}
非递归方式:
优化存储结构:
问题:其中的问题在于,候选解数量很庞大时,采用遍历搜索耗费的时间巨大。
解决:采用不同的筛选方法,减小问题的规模,从而缩短搜索的时间。
方法:回溯法、分支界定法
——————————————————————————————————————————
回溯算法 http://blog.csdn.net/pinkrobin/article/details/5378702
The n-queens puzzle is the problem of placing n queens on an n×n chessboard such that no two queens attack each other.
Given an integer n, return all distinct solutions to the n-queens puzzle.
Each solution contains a distinct board configuration of the n-queens' placement, where
'Q'and
'.'both
indicate a queen and an empty space respectively.
For example,
There exist two distinct solutions to the 4-queens puzzle:
[ [".Q..", // Solution 1 "...Q", "Q...", "..Q."], ["..Q.", // Solution 2 "Q...", "...Q", ".Q.."] ]
思考:
1.总体思路
2.采用什么数据结构
3.需要解决的问题
4.采用什么程序结构
假设棋盘式NxN的二维数组,首先在第一行放置一个Q,接着在第二行放,直到放到第N行,若放置完成则表示找到一种解决方案。如何遍历所有解决方案呢,可以采用递归的方式,使用深度遍历找出所有方案(调用Q(0))。
应该采用什么数据结构呢,若采用二维数组Q
,需要解决A.该行是否有元素 B.该列是否有元素 C.该对角线上是否有元素,这几个应该好解决。若现在要在(row, col)这个点上检查是否可以放皇后,row行没还没放故只用判断row行之前的情况,判断如下:
bool flag = false; //不能放置皇后
for(i = row-1; i >= 1; i--) {
//每行应该判断三个点:Q[i][col+i-row]、 Q[i][col]、 Q[i][col-i+row]
// 可通过判断行列的变化情况找到这三个点
if( Q[i][col+i-row] == 0 && Q[i][col] == 0 && Q[i][col-i+row] ) {
flag = true;
Q[row][col] = 1;
}
}
如果要记录下所有结果呢,也就是所有的二维表结果,应该怎么设计呢? 因为深度遍历每一次从根节点,访问到叶子节点,本身就是一种解决方案,记录该方案即可。采用输出表示记录该方案。
bool isPutQueen(int row, int col) {
bool flag = false;
for(int i = row - 1; i >= 1; i--) {
if(!Q[i][col+i-row] && !Q[i][col] && !Q[i][col-i+row]) {
flag = true;
break;
}
}
return flag;
}
void NQueen(int row) {
if(row == N) {
for(int i = 1; i <= N; i++) {
for(int j = 1; j <= N; j++) {
cout << Q[i][j] << " ";
Q[i][j] = 0;
}
cout << endl;
}
cout << endl;
return ;
} else {
for(int i = 1; i <= N; i++) {
for(int j = 1; j <= N; j++)//回溯法的精髓,记录了前面row-1行的情况
Q[row][j] = 0;
if(isPutQueen(row, i)) {
NQueen(row++);
}
}
}
}
#define N 16
int Q[N + 1][N + 1];
int main() {
InitQueen();
NQueen(1);
return 0;
}
非递归方式:
优化存储结构:
相关文章推荐
- n Queens Problem(回溯法)
- LeetCode OJ N-Queens
- 回溯法——八皇后问题 n-queens
- leetcode做题总结,回溯法(N-Queens, N-QueensII,Combination SumI&II,wordbreak II, SubsetsI&II)
- LeetCode OJ-22.Generate Parentheses(回溯法)
- LeetCode OJ - N-Queens
- LeetCode OJ-- N-Queens **
- LeetCode OJ 之 N-Queens(N皇后)
- LeetCode OJ:N-Queens
- LeetCode OJ:N-Queens(N皇后问题)
- 回溯法之子集和问题
- LeetCode OJ-64.Minimum Path Sum(DP)
- leetcode oj java 230. Kth Smallest Element in a BST
- 494. Target Sum-回溯法、DP。
- 算法: 回溯法大全
- 桥本木分式(使用回溯法求解)
- LeetCode OJ|Array| Find All Numbers Disappeared in an Array
- PAT (Advanced Level) Practise 1128 N Queens Puzzle (20)
- LeetCode OJ 155. Min Stack
- N-Queens