#【八皇后问题】
print("八皇后>>>")
# --典型的回溯问题
# 在第一行尝试为第一个皇后选择位置,在第二行尝试为第二个皇后选择第二个位置,以此类推。在无法为一个皇后选择位置时,回溯它的
# 前一位置,为他选择另一个位置,最后尝试完所有可能性。
# 可以用列表、元组的 下标和下标对应的元素 来表示 行和列的位置
# state1=(0,1,2,3,4),如state1[0] = 1 表示第一行和第二列所占的位置
# conflict(state,nextX)功能:检查下一个皇后的位置是否与以前位置相冲突,不冲突返回False ,否则返回True。
# state----为已经分好位置的皇后所在列数的元组,下标表示棋盘的行数。
# nextX----为下一位置的皇后所在的列数。
def conflict(state,nextX):
nextY = len(state) # 得出已经占有位置的皇后的个数。
for i in range(nextY): # 下一皇后的位置与既有皇后进行比较。(规则:不在一列且不在一个对角线上)
if abs( state[i]-nextX ) in (0, nextY - i): # i:表示第i行,state[i]表示i行皇后所在的列数
return True
return False # 都不冲突返回False
# num: 棋盘的尺寸,
# state: 默认为空元组
def queens(num=8,state=()):
for pos in range(num): # 遍历每一列位置
if not conflict(state,pos): # 满足不冲突的pos时,进入
if len(state) == num-1: # 返回条件(当为最后一个位置时)
yield (pos,)
else: # 进入递归循环
for result in queens(num,state+(pos,)):
yield (pos,) + result
for i in queens(num=4):
print(i)
'''
(1, 3, 0, 2)
(2, 0, 3, 1)
'''
1. 假如棋盘为 4*4 大小,位置摆放的结果有(1,3,0,2)(此位置的皇后分布如下图所示:)和(2,0,3,1)两种。
# | |||
# | |||
# | |||
# |
2.(1,3,0,2)位置分配的递归部分过程