33 N皇后问题
原题网址:https://www.lintcode.com/zh-cn/old/problem/n-queens/#
n皇后问题是将n个皇后放置在n*n的棋盘上,皇后彼此之间不能相互攻击。
给定一个整数n,返回所有不同的n皇后问题的解决方案。
每个解决方案包含一个明确的n皇后放置布局,其中“Q”和“.”分别表示一个女王和一个空位置。
对于4皇后问题存在两种解决的方案:
[
[".Q..", // Solution 1
"...Q",
"Q...",
"..Q."],
["..Q.", // Solution 2
"Q...",
"...Q",
".Q.."]
]
你能否不使用递归完成?
1) 算法开始, 清空棋盘,当前行被设为第一行,当前列被设为第一列(即从0,0处开始扫描)
2) 在当前行,当前列的位置上判断是否满足条件(即保证经过这一点的行,列与斜线上都没有两个皇后),若不满足,跳到第4步
3) 在当前位置上满足条件的情形:
在当前位置放一个皇后,若当前行是最后一行,记录一个解;
若当前行不是最后一行,当前行设为下一行, 当前列设为当前行的第一个待测位置;
以下两步是当前行是最后一行情况下的执行步骤,即找其他解过程:
若当前行是最后一行,当前列不是最后一列,当前列设为下一列;
若当前行是最后一行,当前列是最后一列,回溯,即清空当前行及以下各行的棋盘,然后,当前行设为上一行,当前列设为当前行的下一个待测位置;
以上返回到第2步
4) 在当前位置上不满足条件的情形:
若当前列不是最后一列,当前列设为下一列,返回到第2步;
若当前列是最后一列了,回溯,有两种情况:若当前行已经是第一行了(说明找到所有解),算法退出,否则,清空当前行及以下各行的棋盘,然后,当前行设为上一行,当前列设为当前行的下一个待测位置,返回到第2步;
class Solution {
public:
/*
* @param n: The number of queens
* @return: All distinct solutions
*/
vector<vector<string>> solveNQueens(int n) {
// write your code here
vector<vector<string>> result;
if (n<=)
{
return result;
}
int * position=new int[n];
for (int i=;i<n;i++)
{
position[i]=-;
}
int row=;
placeQueen(result,row,position,n);
delete []position;
return result;
}
void placeQueen(vector<vector<string>> &result,int row,int * position,int n)
{
if (row==n) //最后一行处理完,寻找到一个解决方案,将其字符串数组化push到结果中;
{
string str(n,'.');
vector<string> temp(n,str);
for (int i=;i<n;i++)
{
temp[i][position[i]]='Q';
}
result.push_back(temp);
}
else
{
for (int j=;j<n;j++)//寻找该行可以放置Q的列;
{
if (CanPlaceQ(row,j,position,n))//找到,则继续寻找下一行;
{
position[row]=j;
placeQueen(result,row+,position,n);
}
//找不到,j++,寻找该行的下一列;
}
}
}
bool CanPlaceQ(int row,int col,int * position,int n)
{
for (int i=;i<row;i++)
{
if (position[i]==col||abs(row-i)==abs(col-position[i]))//判断是否在同一列或同一对角线;
{
return false;
}
}
return true;
}
};
递归方法其他参考:https://blog.csdn.net/sinat_26230689/article/details/52206498 这个代码我看了几遍还是很懵……智商捉急,先把他的思路copy过来:
【解题思路】
深度遍历+回溯。
1. 从上到下,从左到右,判断某个位置是否可以放皇后,可以放,转2,不可以,转3;
2. 放置皇后,并判断是否已经放置N个皇后,如果是,记录结果并回溯(寻找其他解决方案);否则转1,递归判断下一行能否放置皇后;
3. 判断本行下一列是否可以放置皇后。如果本列无法放置皇后,剪枝;否则查看下一列能否放置皇后。
即,可以放置,就往下找;放不了,就往回看,拜托上层变一变,看能不能继续往下找,直到第一层都试过最后一列的位置,程序结束。
由于需要记录所有可行结果并输出,在每次得到可行结果时,将当前结果保存,并将Q还原为".",方便回溯。
class Solution {
public:
/*
* @param n: The number of queens
* @return: All distinct solutions
*/
bool CanPlaceQ(int row,int col,int * position,int n)
{
for (int i=;i<row;i++)
{
if (position[i]==col||abs(row-i)==abs(col-position[i]))//判断是否在同一列或同一对角线;
{
return false;
}
}
return true;
}
void placeQueen(vector<vector<string>> &result,int row,int * position,int n)
{
int i=,j=;
while(i<n)
{
while(j<n)
{
if (CanPlaceQ(i,j,position,n))
{
position[i]=j;
j=;//下一行判断时列从头开始;
break; //直接判断下一行;
}
else
{
j++;//当前行当前列无法放Q,判断当前行下一列;
}
}
if (position[i]==-)//当前行没有可以放Q的位置,回溯;
{
if (i==)//回溯到第一行也无解,说明找到所有解,退出程序;
{
break;
}
--i;//否则回溯到上一行;
j=position[i]+;//从上一行可以放Q的下一位开始判断;
position[i]=-;//注意清空上一行位置!!;
continue;
}
if (i==n-) //最后一行判断完且找到放Q位置,将当前解决方案放入结果中;
{
string str(n,'.');
vector<string> temp(n,str);
for (int k=;k<n;k++)
{
temp[k][position[k]]='Q';
}
result.push_back(temp);
j=position[i]+;//此时不能结束,要找下一个解决方案,继续判断当前行下一个位置是否符合要求;
position[i]=-;//注意当前位置的状态要置-1;
continue;
}
i++;
}
}
vector<vector<string>> solveNQueens(int n)
{
vector<vector<string>> result;
if (n<=)
{
return result;
}
int * position=new int[n];
for (int i=;i<n;i++)
{
position[i]=-;
}
int row=;
placeQueen(result,row,position,n);
delete []position;
return result;
}
};
33 N皇后问题的更多相关文章
- dfs 解决八皇后问题 以及其他图搜索问题
33. N皇后问题 中文 English n皇后问题是将n个皇后放置在n*n的棋盘上,皇后彼此之间不能相互攻击(任意两个皇后不能位于同一行,同一列,同一斜线). 给定一个整数n,返回所有不同的n皇后问 ...
- 极限编程,最强N皇后JAVA解题代码,4秒出15皇后,33秒出16皇后
私人博客原文链接来自:http://www.hexcode.cn/article/show/eight-queen 8皇后以及N皇后算法探究,回溯算法的JAVA实现,非递归,循环控制及其优化 8皇后以 ...
- 54. 八皇后问题[eight queens puzzle]
[本文链接] http://www.cnblogs.com/hellogiser/p/eight-queens-puzzle.html [题目] 在8×8的国际象棋上摆放八个皇后,使其不能相互攻击,即 ...
- 八皇后问题 --- 递归解法 --- java代码
八皇后问题是一个以国际象棋为背景的问题:如何能够在 8×8 的国际象棋棋盘上放置八个皇后,使得任何一个皇后都无法直接吃掉其他的皇后?为了达到此目的,任两个皇后都不能处于同一条横行.纵行或斜线上.八皇后 ...
- C语言 · 8皇后问题改编
8皇后问题(改编) 问题描述 规则同8皇后问题,但是棋盘上每格都有一个数字,要求八皇后所在格子数字之和最大. 输入格式 一个8*8的棋盘. 输出格式 所能得到的最大数字和 样例输入 1 2 3 4 5 ...
- 哈密顿绕行世界问题、n皇后问题
哈密顿绕行世界问题 Time Limit: 3000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)Total S ...
- 个人项目Individual Project:n皇后问题
源码的github链接: https://github.com/luhan420/test/tree/master 1.需求分析 在本次的课程设计中,用到的知识点主要有:类.函数.选择结构里的条件语 ...
- 蓝桥杯 算法提高 8皇后·改 -- DFS 回溯
算法提高 8皇后·改 时间限制:1.0s 内存限制:256.0MB 问题描述 规则同8皇后问题,但是棋盘上每格都有一个数字,要求八皇后所在格子数字之和最大. 输入格式 一个8*8 ...
- 20190621-N皇后
N皇后 难度分类 困难 题目描述 n皇后问题研究的是如何将 n个皇后放置在 n×n 的棋盘上,并且使皇后彼此之间不能相互攻击. 上图为 8 皇后问题的一种解法. 给定一个整数 n,返回所有不同的 n ...
随机推荐
- mybatis中的动态SQL语句
有时候,静态的SQL语句并不能满足应用程序的需求.我们可以根据一些条件,来动态地构建 SQL语句. 例如,在Web应用程序中,有可能有一些搜索界面,需要输入一个或多个选项,然后根据这些已选择的条件去执 ...
- sklearn中回归器性能评估方法
explained_variance_score() mean_absolute_error() mean_squared_error() r2_score() 以上四个函数的相同点: 这些函数都有一 ...
- go 函数和流程控制
if/else分支判断 基本结构如下: if condition1 { } if condition1 { } else { } if condition1 { } else if condition ...
- static/extern&const个人理解
//const仅仅用来修饰右边的变量(基本数据变量p,指针变量*p) static NSString *const keyA = @"keyA"; static NSString ...
- iOS开发系列-UIImageView的contentMode
typedef NS_ENUM(NSInteger, UIViewContentMode) { UIViewContentModeScaleToFill, UIViewContentModeScale ...
- bootstrap-----流体布局解析
流体布局容器 容器的width为auto,只是两边加了15px的padding. 流体布局容器 容器的width为auto,只是两边加了15px的padding. <div class=&quo ...
- php+jquery 上拉加载
<script type="text/javascript"> var resflow = true,pages =2; var ps=$("#ids&quo ...
- python 基本常用数据类型
#字典类型 result={1:2222,2:2221111}; result.items();#获取字典中所有元素 result.keys();#获取字典的key result.values();# ...
- C++Builder常用函数
BCB函数集 1.内存分配 函数名称 AllocMem 函数说明 在队中分配指定字节的内存块,并将分配的每一个字节初始化为 0.函数原型如下: void * __fastcall AllocM ...
- 牛客多校第五场 G subsequence 1 最长公共子序列/组合数
题意: 给定两个由数字组成的序列s,t,找出s所有数值大于t的子序列.注意不是字典序大. 题解: 首先特判s比t短或一样长的情况. 当s比t长时,直接用组合数计算s不以0开头的,长度大于t的所有子序列 ...