N 皇后问题的对角函数回溯搜索策略(python代码)

import sys
sys.setrecursionlimit(9999) #设置深度上限
def diag(i, j, n):  # 计算对角线长度
    main_diag = n-abs(i-j)
    if (i+j) <= n+1:
        back_diag = i +j -1
    else:
        back_diag = 2 * n - i - j + 1
    diag_len = max(main_diag, back_diag)
    return diag_len




def place(queen_list, k): # 判断第k个皇后当前的列位置queen_list[k]是否与其它皇后冲突,不冲突返回真,否则返回假
    for i in range(1, k):
        if queen_list[i] == queen_list[k] or abs(queen_list[i] - queen_list[k]) == abs(i - k):
            return False
    return True




def sort_diag(k,n): #按对角线长度排序
    sort_list = [[j, diag(k, j, n)] for j in range(1, n + 1)]
    sort_list.sort(key=lambda x: x[1])
    stack[k] = sort_list
    return stack




def up_track(n,k,queen_list): # 向上回溯
    global up_num
    up_num+=1
    if stack[k].__len__() == 0:
        queen_list[k] = 0
        k = k - 1
        up_track(n, k, queen_list)
    else:
        queen_list[k] = stack[k][0][0]
        try_track(n,k,queen_list)




def try_track(n, k, queen_list): # 当前试探
    global sort_list
    global try_num
    queen_list[k] = stack[k][0][0]
    if place(queen_list, k):
        if k == n:
            return queen_list
        else:
            del stack[k][0]
            k += 1
            sort_diag(k, n)
            try_track(n, k, queen_list)
    else:
        del stack[k][0]
        if len(stack[k]) > 0:
            try_num += 1
            try_track(n, k, queen_list)
        else:
            queen_list[k] = 0
            k = k - 1
            up_track(n, k, queen_list)




# 主函数
# 打印出n皇后的一个解
n = int(input("输入n皇后维数:"))
try_num = 0    # 试探次数
up_num = 0   # 向上回溯
k = 1
stack = [0 for row1 in range(n + 1)]
queen_list = [0 for row2 in range(n + 1)]
sort_diag(1,n)
try_track(n,k,queen_list)
print(queen_list[1:])
print('回溯次数:', try_num + up_num)

参考文章:八皇后问题回溯法Python实现 http://blog.sina.com.cn/s/blog_3fe961ae0100zaph.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值