Python 递归、迷宫问题、八皇后问题

news2024/12/25 0:58:27

递归应用场景

  • 各种数学问题,如八皇后问题、汉诺塔、阶乘问题、迷宫问题、球和篮子问题等
  • 各种算法中也会使用到递归,比如快排、归并排序、二分查找、分治算法等
  • 能够用栈解决的问题
  • 递归的优点就是代码比较简洁

迷宫问题(Python版)

迷宫示意图, 红色部分表示墙,绿色部分表示通路,第一张图为初始迷宫,第二张为回溯之后的迷宫

      

代码实现

class MiGong:
    def __init__(self):
        # 创建一个 8*7 嵌套列表,模拟迷宫
        self.map = []
        row = 8
        col = 7
        # 初始化迷宫
        # 1表示墙,0表示可通行
        # 将第0行设置为墙
        for i in range(row):
            ls = []
            for j in range(col):
                if i == 0 or i == 7 or j == 0 or j == 6:
                    ls.append(1)
                else:
                    ls.append(0)
            self.map.append(ls)
        self.map[3][1] = 1
        self.map[3][2] = 1
        self.map[4][3] = 1

        self.print_map()

    # 打印迷宫
    def print_map(self):
        row = len(self.map)
        col = len(self.map[0])
        for i in range(row):
            for j in range(col):
                print(self.map[i][j], end=' ')
            print()
        print()

    def find_way(self, i: int, j: int) -> True:
        """
        map: 表示迷宫地图
        (i, j): 老鼠的起始位置
        map[i][j] = 0: 表示该位置没有走过
        map[i][j] = 1: 表示该位置是墙(走不了)
        map[i][j] = 2: 表示该位置是通路(可以走)
        map[i][j] = 3: 表示这个位置是死路上的一个节点(走不了)
        寻路策略:下 -> 右 -> 上 -> 左
        map[6][5] = 2 表示走到了终点(终点位置为(6,5))
        """
        if self.map[6][5] == 2:
            return True
        else:
            if self.map[i][j] == 0:
                # 假设可以走通,先设为2
                self.map[i][j] = 2
                if self.find_way(i + 1, j):  # 向下走
                    return True
                elif self.find_way(i, j + 1):  # 向右走
                    return True
                elif self.find_way(i - 1, j):  # 向上走
                    return True
                elif self.find_way(i, j - 1):  # 向左走
                    return True
                else:  # 死路,走不通,设为3
                    self.map[i][j] = 3
                    return False
            else:  # self.map[i][j] == 1,2,3 ,都表示走不通或已走过
                return False


mg = MiGong()
mg.find_way(1, 1)
mg.print_map()

八皇后问题

思路分析

1、先将第一个皇后放在第一行第一列的位置
2、第二个皇后先放在第二行第一列的位置,然后判断是否冲突,如果冲突,则放在第二行第二列,继续判断,如果冲突,将第二个皇后放在第二行第三列... 依次把第二行所有列都尝试一遍,直到找到合适的一列,摆放第二个皇后
3、接着摆放第三个皇后,依次尝试放在第三行的第一列、第二列、第三列...直到找到一个合适的列摆放第三个皇后
4、同样的摆放第四个、第五个、第六个、第七个、第八个皇后,当第八个皇后也放到第八行的正确位置时,此时找到了一个正确解
5、当第八个皇后摆放好后,即第八个皇后第一次找到正确的位置后,开始回溯,查找其他摆放方法,即将第一个皇后放在第一行第一列这个位置上的所有正确解找出来
6、然后将第一个皇后放在第一行第二列的位置,重复 2-5 的步骤
7、依次将第一个皇后放在第一行第三、四、五、六、七、八列的位置,重复 2-5 的步骤,得到八皇后问题的全部解法(92)

说明:理论上棋盘应该是一个二维数组,但是实际上可以通过算法,用一个一维数组解决,一维数组的下标对应行标,数组的元素对应列标,如 arr[8] = [0, 4, 7, 5, 2, 6, 1, 3] 表示:
    第一个皇后放在第 0 行 第 0 列的位置
    第二个皇后放在第 1 行 第 4 列的位置
    第三个皇后放在第 2 行 第 7 列的位置
    第四个皇后放在第 3 行 第 5 列的位置
    第五个皇后放在第 4 行 第 2 列的位置
    第六个皇后放在第 5 行 第 6 列的位置
    第七个皇后放在第 6 行 第 1 列的位置
    第八个皇后放在第 7 行 第 3 列的位置
即 arr[i] = val 表示第 i 个皇后摆放的位置是第 i 行 第 val 列

代码实现

class Queen:
    count = 0  # 全部的正确解

    def __init__(self, num: int):
        self.num = num  # 皇后的数量
        # 用列表表示一维数组,记录皇后摆放的正确位置
        self.arr = []
        # 初始化数组
        for i in range(num):
            self.arr.append(-1)

    def check_position(self, n: int) -> bool:
        """
        摆放第 n 个皇后在某个位置时,判断是否与前面的 n-1 皇后产生冲突,不冲突返回True
        n 从 0 开始
        """
        for i in range(n):
            # arr[i] = val 表示第 i 个皇后摆放的位置是第 i 行 第 val 列
            if self.arr[i] == self.arr[n]:  # 有两个皇后在同一列
                return False

            # if n - i == self.arr[n] - self.arr[i]:  # 有两个皇后在正对角线上
            #     # 正对角线判断:x2 - x1 == y2 - y1
            #     # (x1, y1) = (i, self.arr[i])
            #     # (x2, y2) = (n, self.arr[n])
            #     return False
            # if n - i == self.arr[i] - self.arr[n]:  # 有两个皇后在反对角线上
            #     # 反对角线上判断:x2 - x1 == y1 - y2
            #     # (x1, y1) = (i, self.arr[i])
            #     # (x2, y2) = (n, self.arr[n])
            #     return False

            # 合并在一起写
            if abs(n - i) == abs(self.arr[n] - self.arr[i]):  # 有两个皇后在对角线上
                return False

        return True

    def place_queen(self, n: int):
        """放置第 n 个皇后,n 从0开始"""
        if n == self.num:  # 全部皇后已经放完,得到一个正确解
            self.count += 1
            print(f'第{self.count}种的解法为{self.arr}')
            return
        # 从第 n 行的第一列开始,依次尝试放置这第 n 个皇后,
        # 看哪个位置可以放,即不会与前面的 n-1 个皇后产生冲突
        for i in range(self.num):  # i 表示列数
            self.arr[n] = i  # 把第 n 个皇后放置在第 n 行第 i 列
            # 检查把第 n 个皇后放置在第 n 行第 i 列后是否与前面的 n-1 个皇后产生冲突
            if self.check_position(n):  # 不产生冲突
                # 如果不产生冲突,则确定了该皇后的放置位置,则开始放置下一个皇后
                self.place_queen(n + 1)

            # 如果冲突,标明第 n 行的第 i 列不能放,继续尝试第 i+1 列

    def print_arr(self):
        """打印数组"""
        for i in self.arr:
            print(i, end=' ')
        print()


q = Queen(8)
q.place_queen(0)  # 从第一个皇后开始,从 0 开始
print('八皇后的全部解法有%s种' % q.count)

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/988916.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

武警三维数字沙盘电子沙盘虚拟现实模拟推演大数据人工智能开发教程第15课

部队三维数字沙盘电子沙盘虚拟现实模拟推演大数据人工智能开发教程第15课 现在不管什么GIS平台首先要解决的就是数据来源问题,因为没有数据的GIS就是一个空壳,下面我就目前一些主流的数据获取 方式了解做如下之我见(主要针对互联网上的一些…

阿里云APP备案步骤_完成工信部APP备案

完成工信部APP备案工作,阿小云分享阿里云App备案详细流程,阿里云APP备案流程分为6步,APP备案成功后应用可以上架,登录阿里云账号填写APP信息,等待阿里云初审,初审通过后进行工信部短信核验,管局…

如何修改VS2017、VS2019、VS2022中C++默认版本

首先明确VS各个版本对C标准的支持情况: IC版本 VS版本 支持情况 C11 2015完全支持 ,13基本支持,12部分支持,10以及以下不支持 完全支持 C14 2017完全支持 ,15基本支持,13部分支持 完全支…

leetcode刷题--数组类

文章目录 1. 485 最大连续1的个数2. 495 提莫攻击3. 414 第三大的数4. 628 三个数的最大乘积5. 645 错误的集合6. 697 数组的度7. 448 找到所有数组中消失的数字9. 41 缺失的第一个正数10. 274 H指数11. 453 最小操作次数使得数组元素相等12. 665 非递减数列13. 283 移动零14. …

Win10下使用vim9

作为一个经常与文字打交道的Writer,你在学会Vim的基本操作之后,就一定会爱上Vim的。 以下是Windows10_64位(专业版)环境中安装、使用Vim9的全过程,分享一下: 一、下载、安装Vim9 去Vim官网去下载最新的Vi…

后端开发进阶之路:后端开发核心竞争力之一抽象建模能力

0.引言 在互联网行业,软件工程师面对的产品需求大都是以具象的现实世界事物概念来描述的,遵循的是人类世界的自然语言,而软件世界里通行的则是机器语言,两者间跨度太大,需要一座桥梁来联通,抽象建模便是打…

Vue 报错error:0308010C:digital envelope routines::unsupported 解决方案(三种)

新换的电脑,系统装的win11,node也是18的版本。 跑了一下老项目,我用的是HbuilderX,点击运行和发行时,都会报错: Error: error:0308010C:digital envelope routines::unsupported 出现这个错误是因为 node.j…

024 - STM32学习笔记 - 液晶屏控制(一) - LTDC与DMA2D初始

024- STM32学习笔记 - LTDC控制液晶屏 在学习如何控制液晶屏之前,先了解一下显示屏的分类,按照目前市场上存在的各种屏幕材质,主要分为CRT阴极射线管显示屏、LCD液晶显示屏、LED显示屏、OLED显示屏,在F429的开发板上,…

工作流-flowable

1. 工作流概述 1.1 概念 工作流(Workflow),就是通过计算机对业务流程自动化执行管理。它主要解决的是“使在多个参与者之间按照某种预定义的规则自动进行传递文档、信息或任务的过程,从而实现某个预期的业务目标,或者促使此目标的实现”。 …

图解系列 图解直播推拉流流程

文章目录 流程推流流程扩展 拉流流程 文件加密流程 常用开源流媒体服务器为SRS和MTX 流程 涉及到的组件 主播(推流端)观众(播放器)业务服务【持有一些私有Key,如rtmpKey等】流媒体服务器【SRS/MTX】CDN【持有公钥】 …

2023-大数据应用开发-电商可视化结果汇总

电商可视化 任务一:用柱状图展示消费额最高的省份 编写Vue工程代码,根据接口,用柱状图展示2020年消费额最高的5个省份,同时将用于图表展示的数据结构在浏览器的console中进行打印输出,将图表可视化结果和浏览器conso…

JavaWeb_LeadNews_Day11-KafkaStream实现实时计算文章分数

JavaWeb_LeadNews_Day11-KafkaStream实现实时计算文章分数 KafkaStream概述案例-统计单词个数SpringBoot集成 实时计算文章分值来源Gitee KafkaStream 概述 Kafka Stream: 提供了对存储与Kafka内的数据进行流式处理和分析的功能特点: Kafka Stream提供了一个非常简单而轻量的…

使用python爬取网站html代码

提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档 目录 前言一、Requests是什么?二、使用步骤1.引入库2.创建一个Faker对象:3.设置要访问的目标网站的URL:4.定义HTTP请求头部:6.…

【python手写算法】正则化在线性回归和逻辑回归中的应用

多元线性回归: # codingutf-8 import matplotlib.pyplot as plt import numpy as np from mpl_toolkits.mplot3d import Axes3Dif __name__ __main__:X1 [12.46, 0.25, 5.22, 11.3, 6.81, 4.59, 0.66, 14.53, 15.49, 14.43,2.19, 1.35, 10.02, 12.93, 5.93, 2.92,…

day 51 |● 503.下一个更大元素II ● 42. 接雨水

503.下一个更大元素II 显示的是循环链表&#xff0c;所以需要遍历两遍。 用i%len(nums)保证循环两遍即可。 func nextGreaterElements(nums []int) []int {res : make([]int, len(nums))for i : 0; i < len(nums); i{res[i] -1}stack : make([]int, 0)stack append(stac…

VoxWeekly|The Sandbox 生态周报|20230904

欢迎来到由 The Sandbox 发布的《VoxWeekly》。我们会在每周发布&#xff0c;对上一周 The Sandbox 生态系统所发生的事情进行总结。 如果你喜欢我们内容&#xff0c;欢迎与朋友和家人分享。请订阅我们的 Medium 、关注我们的 Twitter&#xff0c;并加入 Discord 社区&#xf…

便利连锁店这波操作,赚麻了!

在当今数字化时代&#xff0c;零售业经历了前所未有的革命性变革。消费者期望在购物时获得更多的便捷性、个性化体验和高度智能化的服务。为了满足这些需求&#xff0c;零售商们不得不重新思考他们的经营模式&#xff0c;并将目光投向了新零售模式的未来。 新零售模式不再局限于…

来看看什么是:编译型语言和解释型语言的区别

通过高级语言编写的源码&#xff0c;我们能够轻松理解&#xff0c;但对于计算机来说&#xff0c;它只认识二进制指令&#xff0c;源码就是天书&#xff0c;根本无法识别。源码要想执行&#xff0c;必须先转换成二进制指令。 所谓二进制指令&#xff0c;也就是由 0 和 1 组成的…

非插座式水壶/插座式水壶:SOR/2016-181(水壶法规)和CSA 22.1标准解读!

电水壶作为一种常见的小家电&#xff0c;受到了广大消费者的喜爱。然而&#xff0c;由于安全问题的日益重视&#xff0c;亚马逊加拿大站决定加强对电水壶产品的审核&#xff0c;以确保消费者的安全和权益。 近日&#xff0c;亚马逊平台发布公告&#xff0c;要求在加拿大站销售…

C/C++苹果和虫子 2019年9月电子学会青少年软件编程(C/C++)等级考试一级真题答案解析

目录 C/C苹果和虫子 一、题目要求 1、编程实现 2、输入输出 二、解题思路 1、案例分析 三、程序代码 四、程序说明 五、运行结果 六、考点分析 C/C苹果和虫子 2019年9月 C/C编程等级考试一级编程题 一、题目要求 1、编程实现 你买了一箱n个苹果&#xff0c;很不幸…