51. N 皇后
n 皇后问题 研究的是如何将 n 个皇后放置在 n×n 的棋盘上,并且使皇后彼此之间不能相互攻击。
给你一个整数 n ,返回所有不同的 n 皇后问题 的解决方案。
每一种解法包含一个不同的 n 皇后问题 的棋子放置方案,该方案中 ‘Q’ 和 ‘.’ 分别代表了皇后和空位。
示例 1:
输入:n = 4
输出:[[".Q…","…Q",“Q…”,"…Q."],["…Q.",“Q…”,"…Q",".Q…"]]
解释:如上图所示,4 皇后问题存在两个不同的解法。
示例 2:
输入:n = 1
输出:[[“Q”]]
提示:
1 <= n <= 9
来源:力扣(LeetCode)
链接:https://leetcode-cn.com/problems/n-queens
著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。
分析
参考:https://github.com/youngyangyang04/leetcode-master/blob/master/problems/0051.N%E7%9A%87%E5%90%8E.md
题解(Java)
class Solution {
List<List<String>> ans = new ArrayList<>();
public List<List<String>> solveNQueens(int n) {
//用二维数组代表棋盘
char[][] chessboard = new char[n][n];
//初始化棋盘
for (char[] c : chessboard) {
Arrays.fill(c, '.');
}
backTracking(n, chessboard, 0);
return ans;
}
private void backTracking(int n, char[][] chessboard, int row) { //row代表棋盘的列
if (row == n) {
ans.add(fillAns(chessboard)); //收集当前放好的棋盘结果
return;
}
//按棋盘的行遍历
for (int col = 0; col < n; col++) {
if (judge(row, col, n, chessboard)) { //判断要加入的位置是否冲突
chessboard[row][col] = 'Q';
backTracking(n, chessboard, row + 1);
chessboard[row][col] = '.';
}
}
}
private List<String> fillAns(char[][] chessboard) { //收集当前放好的棋盘结果
List<String> list = new ArrayList<>();
for (char[] c : chessboard) {
list.add(String.copyValueOf(c));
}
return list;
}
private boolean judge(int row, int col, int n, char[][] chessboard) {
//判断同行有没有皇后,只需要判断当前列前面的行,同列不需要判断有没有
for (int i = 0; i < row; i++) {
if (chessboard[i][col] == 'Q') {
return false;
}
}
//判断左上45度对角线有没有皇后
for (int i = row - 1, j = col - 1; i >= 0 && j >= 0; i--, j--) {
if (chessboard[i][j] == 'Q') {
return false;
}
}
//判断左下45度对角线有没有皇后
for (int i = row - 1, j = col + 1; i >= 0 && j <= n - 1; i--, j++) {
if (chessboard[i][j] == 'Q') {
return false;
}
}
return true;
}
}