赞
踩
题目描述:
在 n\times nn×n 的棋盘上放置 nn 个皇后,求所有的放置方法。
放置时要满足:任意两个皇后不能在同一行、同一列,也不能在同一条对角线上。
给定 nn,输出所有合法的放置方案。
输入格式
一个整数 nn。
输出格式
每个解占 nn 行,其中第 ii 行为皇后所在的列编号,按字典序从小到大输出所有的解,每个解之间要用一个空行隔开。
最后一行输出总方案数。
样例输入
4
样例输出
2 4 1 3 3 1 4 2
4 2 1 3 2 4 3 1
解析:
这道题是一个经典的 “八皇后问题”,它的思路是深度优先搜索 + 剪枝。
我们可以从第 11 行开始往下依次考虑放哪个位置的皇后,尝试将其放在 1\sim n1∼n 中的第 ii 列,并判断是否合法。若该位置合法,再考虑填下一行;若不合法则直接跳过这个位置。
在搜索时,我们需要维护三个状态:
每次循环枚举的是 1\sim n1∼n 中的第 ii 列,如果在同一列(cols[i])或者对角线上(diagonal[i-j+n] 或 anti_diagonal[i+j])已经有了皇后,则直接跳过。否则就将当前位置标记为皇后,并更新三个状态的值,然后进入下一层递归搜索。
终止条件是当前搜索到了最后一行,即搜索到第 n+1n+1 行。
最后,我们统计合法解的数量,并输出所有合法方案。
详细python代码:
- def solveNQueens(n: int) -> List[List[str]]:
- def dfs(row):
- # 搜索到了第 n + 1 行,记录答案
- if row == n:
- res.append([''.join(s) for s in board])
- return
-
- for col in range(n):
- # 判断当前位置能否放置皇后
- if not cols[col] and not diagonal[row - col + n] and not anti_diagonal[row + col]:
- cols[col] = True
- diagonal[row - col + n] = True
- anti_diagonal[row + col] = True
- board[row][col] = 'Q'
-
- dfs(row + 1)
-
- cols[col] = False
- diagonal[row - col + n] = False
- anti_diagonal[row + col] = False
- board[row][col] = '.'
-
- res = []
- # 初始化棋盘为全空状态
- board = [['.' for _ in range(n)] for _ in range(n)]
- # 列
- cols = [False] * n
- # 右上至左下的斜线
- diagonal = [False] * (2 * n - 1)
- # 左上至右下的斜线
- anti_diagonal = [False] * (2 * n - 1)
-
- dfs(0)
-
- return res
其中,dfs
函数是核心搜索函数,其参数 row
表示当前正在搜索第几行。在搜索过程中,我们维护了四个状态:棋盘状态 board
、列状态 cols
、右上至左下的斜线状态 diagonal
和左上至右下的斜线状态 anti_diagonal
。在搜索到第 n+1
行时,我们将当前棋盘状态加入到答案中。
主函数初始化了棋盘和四个状态,并从第 0 行开始调用 dfs
函数进行搜索,最终返回答案。
注意:本代码使用了 Python 中的 Type Hints,需要 Python 3.5 及以上版本才能运行。
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。