LeetCode-Python-51. N皇后

皇后问题研究的是如何将 n 个皇后放置在 n×n 的棋盘上,并且使皇后彼此之间不能相互攻击。

上图为 8 皇后问题的一种解法。

给定一个整数 n,返回所有不同的 皇后问题的解决方案。

每一种解法包含一个明确的 n 皇后问题的棋子放置方案,该方案中 'Q' 和 '.' 分别代表了皇后和空位。

示例:

输入: 4
输出: [
 [".Q..",  // 解法 1
  "...Q",
  "Q...",
  "..Q."],

 ["..Q.",  // 解法 2
  "Q...",
  "...Q",
  ".Q.."]
]
解释: 4 皇后问题存在两个不同的解法。

思路:

一道经典的回溯题,十年前就学过了,现在才真的能写出来……惭愧惭愧

核心思想就是回溯,尝试每一种可能的下法,如果不满足条件,就倒退回上一次的状态。

判断皇后冲突时,

1. 横向冲突就是Y相同,X不同的位置上出现了别的Q

2. 竖向冲突就是X相同,Y不同的位置上出现了别的Q

3. /向冲突就是 X + Y的和 相同的坐标上出现了别的Q

4. \向冲突就是 Y - X的差 相同的坐标上出现了别的Q

class Solution(object):
    def solveNQueens(self, n):
        """
        :type n: int
        :rtype: List[List[str]]
        """
        board = ["." * n for _ in range(n)]

        res = []
        def checkRowAndCol(row, col):
            for i in range(n):
                if (board[row][i] == "Q" and i != col) or (board[i][col] == "Q" and i != row): #发生了横向或者纵向冲突
                    return False
            return True
        
        def checkDoubleDio(row, col):
            add = row + col
            sub = col - row
            
            for x in range(n):
                if x == row: #跳过自身这个点
                    continue
                y = add - x
                # print add,sub, x, y
                if y >= 0 and y < n and x >= 0 and x < n and board[x][y] == "Q": #发生/冲突
                    return False
            
                y = sub + x
                if y >= 0 and y < n and x >= 0 and x < n and board[x][y] == "Q": #发生\冲突
                    return False
                
            return True
        
        
        def dfs(row, col):
            if col >= n: #本行所有位置都找完了
                return
            board[row] = "." * col + "Q" + (n - col - 1) * "." #把皇后放在(row, col)的位置上
            if checkRowAndCol(row, col) and checkDoubleDio(row, col): #如果没有发生冲突
                if row == n - 1: #如果放下的是最后一个皇后
                    # print board
                    res.append(board[:]) #找到一个可行解啦!!!
                else:
                    for i in range(n): #还要放更多的皇后,往下一行放吧
                        dfs(row + 1, i)
                        
            board[row] = "." * n #回溯,把本行放下的皇后拿回来
            # dfs(row, col + 1)
            return

        for i in range(n):
            dfs(0, i)
            
        return res

猜你喜欢

转载自blog.csdn.net/qq_32424059/article/details/90109415