n皇后问题算法介绍
N皇后问题是一个经典的回溯算法问题,属于组合优化中的放置问题。问题目标是在N×N的棋盘上放置N个皇后,使得她们互不攻击,即任意两个皇后都不在同一行、同一列或同一对角线上。
下面是N皇后问题的一种常见解法,使用回溯法(Backtracking)来实现:
Python 示例代码
def is_safe(board, row, col, n):
# 检查列上是否有皇后冲突
for i in range(row):
if board[i] == col:
return False
# 检查左上对角线是否有皇后冲突
for i, j in zip(range(row-1, -1, -1), range(col-1, -1, -1)):
if board[i] == j:
return False
# 检查右上对角线是否有皇后冲突
for i, j in zip(range(row-1, -1, -1), range(col+1, n)):
if board[i] == j:
return False
return True
def solve_n_queens(n):
def place_queen(row, board):
if row >= n:
# 如果所有行都放置了皇后,则找到了一个解决方案
result.append(board[:])
return
for col in range(n):
if is_safe(board, row, col, n):
board[row] = col
place_queen(row + 1, board)
board[row] = -1 # 回溯,撤销选择
result = []
board = [-1] * n # 使用数组来记录每一行皇后的列位置,-1 表示尚未放置
place_queen(0, board)
return result
# 调用函数
n = 4 # 例如,4皇后问题
solutions = solve_n_queens(n)
# 打印所有解决方案
for solution in solutions:
for row in solution:
print(" ".join(".Q"[col != row] for col in range(n)))
print()
代码说明
is_safe 函数检查在棋盘的 (row, col) 位置放置皇后是否安全。
solve_n_queens 函数定义了递归函数 place_queen 来放置皇后。它首先检查是否已经将所有皇后放置完毕(即 row >= n),如果是,则将当前棋盘状态添加到结果列表中。否则,它尝试在当前行的每一列放置皇后,并递归地放置下一行的皇后。
在递归调用 place_queen 之前,将皇后放置在 (row, col) 位置,并在递归调用之后,通过 board[row] = -1 撤销该选择,以尝试下一个可能的列位置。
该算法通过递归和回溯来探索所有可能的棋盘布局,并只保留那些满足N皇后条件的布局。
n皇后问题算法python实现样例
以下是使用递归回溯的方法来解决N皇后问题的Python实现:
def solveNQueens(n):
def is_valid(board, row, col):
# 检查同列是否有皇后冲突
for i in range(row):
if board[i] == col:
return False
# 检查对角线是否有皇后冲突
if abs(board[i] - col) == abs(i - row):
return False
return True
def backtrack(board, row):
# 找到一个解,保存结果
if row == n:
res.append(board[:])
return
for col in range(n):
if not is_valid(board, row, col):
continue
# 更新当前行的状态
board[row] = col
# 进入下一行的决策
backtrack(board, row + 1)
res = []
board = [-1] * n # 初始化棋盘
backtrack(board, 0) # 从第一行开始回溯
return res
n = 4
solutions = solveNQueens(n)
print(f"共有 {
len(solutions)} 种摆放方法:")
for solution in solutions:
for row in range(n):
line = ""
for col in range(n):
if solution[row] == col:
line += "Q "
else:
line += ". "
print(line)
print()
运行以上代码,您将得到在4x4棋盘上的2种解法:
Q . . .
. . Q .
. . . Q
. Q . .
. Q . .
. . . Q
Q . . .
. . Q .
注意,此代码解决的是通用的N皇后问题,对于大型的N可能会有较长的运行时间。