[LeetCode] 51. N-Queens N皇后问题
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.
Example:
Input: 4 Output: [ [".Q..", // Solution 1 "...Q", "Q...", "..Q."], ["..Q.", // Solution 2 "Q...", "...Q", ".Q.."] ] Explanation: There exist two distinct solutions to the 4-queens puzzle as shown above.
八皇后问题扩展到N皇后,经典的回溯算法题。
解法:回溯Backtracking
Java:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 | public class Solution { public List<List<String>> solveNQueens( int n) { char [][] board = new char [n][n]; for ( int i = 0 ; i < n; i++) for ( int j = 0 ; j < n; j++) board[i][j] = '.' ; List<List<String>> res = new ArrayList<List<String>>(); dfs(board, 0 , res); return res; } private void dfs( char [][] board, int colIndex, List<List<String>> res) { if (colIndex == board.length) { res.add(construct(board)); return ; } for ( int i = 0 ; i < board.length; i++) { if (validate(board, i, colIndex)) { board[i][colIndex] = 'Q' ; dfs(board, colIndex + 1 , res); board[i][colIndex] = '.' ; } } } private boolean validate( char [][] board, int x, int y) { for ( int i = 0 ; i < board.length; i++) { for ( int j = 0 ; j < y; j++) { if (board[i][j] == 'Q' && (x + j == y + i || x + y == i + j || x == i)) return false ; } } return true ; } private List<String> construct( char [][] board) { List<String> res = new LinkedList<String>(); for ( int i = 0 ; i < board.length; i++) { String s = new String(board[i]); res.add(s); } return res; } } |
Python:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 | class Solution( object ): def solveNQueens( self , n): """ :type n: int :rtype: List[List[str]] """ def dfs(curr, cols, main_diag, anti_diag, result): row, n = len (curr), len (cols) if row = = n: result.append( map ( lambda x: '.' * x + "Q" + '.' * (n - x - 1 ), curr)) return for i in xrange (n): if cols[i] or main_diag[row + i] or anti_diag[row - i + n]: continue cols[i] = main_diag[row + i] = anti_diag[row - i + n] = True curr.append(i) dfs(curr, cols, main_diag, anti_diag, result) curr.pop() cols[i] = main_diag[row + i] = anti_diag[row - i + n] = False result = [] cols, main_diag, anti_diag = [ False ] * n, [ False ] * ( 2 * n), [ False ] * ( 2 * n) dfs([], cols, main_diag, anti_diag, result) return result |
Python:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 | # For any point (x,y), if we want the new point (p,q) don't share the same row, column, or diagonal. # then there must have ```p+q != x+y``` and ```p-q!= x-y``` # the former focus on eliminate 'left bottom right top' diagonal; # the latter focus on eliminate 'left top right bottom' diagonal # - col_per_row: the list of column index per row # - cur_row:current row we are seraching for valid column # - xy_diff:the list of x-y # - xy_sum:the list of x+y class Solution2( object ): def solveNQueens( self , n): """ :type n: int :rtype: List[List[str]] """ def dfs(col_per_row, xy_diff, xy_sum): cur_row = len (col_per_row) if cur_row = = n: ress.append(col_per_row) for col in range (n): if col not in col_per_row and cur_row - col not in xy_diff and cur_row + col not in xy_sum: dfs(col_per_row + [col], xy_diff + [cur_row - col], xy_sum + [cur_row + col]) ress = [] dfs([], [], []) return [[ '.' * i + 'Q' + '.' * (n - i - 1 ) for i in res] for res in ress] |
C++:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 | class Solution { public : vector<vector<string> > solveNQueens( int n) { vector<vector<string> > res; vector< int > pos(n, -1); solveNQueensDFS(pos, 0, res); return res; } void solveNQueensDFS(vector< int > &pos, int row, vector<vector<string> > &res) { int n = pos.size(); if (row == n) { vector<string> out(n, string(n, '.' )); for ( int i = 0; i < n; ++i) { out[i][pos[i]] = 'Q' ; } res.push_back(out); } else { for ( int col = 0; col < n; ++col) { if (isValid(pos, row ,col)) { pos[row] = col; solveNQueensDFS(pos, row + 1, res); pos[row] = -1; } } } } bool isValid(vector< int > &pos, int row, int col) { for ( int i = 0; i < row; ++i) { if (col == pos[i] || abs (row - i) == abs (col - pos[i])) { return false ; } } return true ; } }; |
类似题目:
[LeetCode] 52. N-Queens II N皇后问题 II
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 10年+ .NET Coder 心语,封装的思维:从隐藏、稳定开始理解其本质意义
· .NET Core 中如何实现缓存的预热?
· 从 HTTP 原因短语缺失研究 HTTP/2 和 HTTP/3 的设计差异
· AI与.NET技术实操系列:向量存储与相似性搜索在 .NET 中的实现
· 基于Microsoft.Extensions.AI核心库实现RAG应用
· 10年+ .NET Coder 心语 ── 封装的思维:从隐藏、稳定开始理解其本质意义
· 地球OL攻略 —— 某应届生求职总结
· 提示词工程——AI应用必不可少的技术
· Open-Sora 2.0 重磅开源!
· 周边上新:园子的第一款马克杯温暖上架