经典回溯算法解析

八皇后问题

要求在8×8的国际象棋棋盘上放置8个皇后,使得它们互不攻击(即任意两个皇后不在同一行、同一列或同一对角线上)。

python 复制代码
# 统计所有合法摆放方式的数量
def eight_queens():
    count = 0  # 统计合法解的数量
    # 初始化占用标记数组(索引1-8有效,0弃用)
    row_use = [False] * 9  # 行占用(实际按行递归,这个数组其实用不上,可删)
    col_use = [False] * 9  # 列占用
    zhu_use = [False] * 17  # 主对角线
    fu_use = [False] * 17  # 副对角线

    # 回溯函数:处理第row行的皇后放置(必须嵌套在eight_queens内,否则访问不到外部变量)
    def back(row):
        nonlocal count
        # 终止条件:8行全部放置完成,找到一个合法解
        if row > 8:
            count += 1
            return

        # 遍历当前行的所有列(1-8,col=扣)
        for col in range(1, 9):
            # 核心判断:列、主对角线、副对角线都未被占用
            if not col_use[col] and not zhu_use[row + col] and not fu_use[row - col + 8]:
                # 标记占用(放置皇后)
                col_use[col] = True
                zhu_use[row + col] = True
                fu_use[row - col + 8] = True

                # 递归处理下一行
                back(row + 1)

                # 回溯:取消标记(移除皇后)
                col_use[col] = False
                zhu_use[row + col] = False
                fu_use[row - col + 8] = False

    # 从第1行开始回溯(调用回溯函数,缩进必须在eight_queens内)
    back(1)
    # 返回最终统计结果
    return count


# 定义main函数,调用eight_queens并输出结果
def main():
    result = eight_queens()
    print(result)  # 输出:92


# 执行入口
if __name__ == "__main__":
    main()

数独填数问题

37. 解数独 - 力扣(LeetCode)

数独是一种逻辑游戏,需要在9x9的格子中填入数字1-9,满足以下条件:

  • 每一行必须包含数字1-9且不重复。
  • 每一列必须包含数字1-9且不重复。
  • 每个3x3的小宫格(共9个)必须包含数字1-9且不重复。
python 复制代码
# 检查(x,y)位置填入num是否合法
def is_valid(board, x, y, num):
    # 检查行
    for i in range(9):
        if board[x][i] == num:
            return False
    # 检查列
    for i in range(9):
        if board[i][y] == num:
            return False
    # 检查3×3宫
    sx = x // 3 * 3
    sy = y // 3 * 3
    for i in range(3):
        for j in range(3):
            if board[sx+i][sy+j] == num:
                return False
    return True

# DFS回溯求解数独
def dfs(board):
    for i in range(9):
        for j in range(9):
            if board[i][j] == 0:
                for num in range(1, 10):
                    if is_valid(board, i, j, num):
                        board[i][j] = num
                        if dfs(board):
                            return True
                        board[i][j] = 0  # 回溯
                return False
    return True

# 主程序
if __name__ == "__main__":
    board = []
    # 读取9行空格分隔的数独输入(0表示空白)
    for _ in range(9):
        line = input().strip()
        row = list(map(int, line.split()))
        board.append(row)
    # 求解并按标准格式输出
    if dfs(board):
        for row in board:
            print(' '.join(map(str, row)))
    else:
        print("无解")
核心点 数独 / 皇后问题通用逻辑
回溯核心 「试填→验证→递归→回溯」:试选一个值→验证合法性→递归填下一个→错了就回退(恢复现场)
终止条件 所有位置填完(数独无 0 / 皇后放满 N 个)→返回 True;某位置无合法值→返回 False 触发回溯
核心价值 暴力枚举的优化:提前剪枝(非法值不递归),避免无效计算,适配蓝桥杯中等难度算法题
相关推荐
水木流年追梦8 小时前
大模型入门-大模型优化方法13- MTP 多 token 输出、DCA 双块注意力
人工智能·分布式·算法·正则表达式·prompt
数据皮皮侠8 小时前
全国消协智慧 315 平台投诉信息数据库
大数据·人工智能·算法·百度·制造
清水白石0088 小时前
从打印对象到高质量调试:彻底理解 Python 中 `__repr__` 和 `__str__` 的区别
开发语言·python
8Qi88 小时前
LeetCode 115 & 392:不同子序列 / 判断子序列
算法·leetcode·职场和发展·动态规划
Sammyyyyy9 小时前
Google I/O 2026 Antigravity 更新解析与 SDK 实战指南
python·ai编程·servbay
小蒋学算法9 小时前
算法-乘法表中第K小的数-二分
数据结构·算法
智者知已应修善业9 小时前
【51单片机8个LED,已经使用了D1D2,怎么样在不动D1D2的前提下实现D6~D8的流水灯】2024-1-19
c++·经验分享·笔记·算法·51单片机
Evand J9 小时前
【MATLAB例程】自适应渐消扩展卡尔曼滤波(AFEKF)三维雷达目标跟踪|效果已调优,附下载链接和运行结果,代码直接运行即可
开发语言·算法·matlab·目标跟踪·卡尔曼滤波·自适应滤波·代码定制
嫂子的姐夫9 小时前
047-MD5:飞卢网
爬虫·python·js逆向·逆向
DXM05219 小时前
第8期| 传统机器学习遥感解译:SVM & 随机森林分类全流程实操
人工智能·python·随机森林·机器学习·支持向量机·arcgis·自然语言处理