(一)、python程序--模拟电脑鼠走迷宫

news2024/11/14 6:43:00

一、绪论

1、简介

电脑鼠走迷宫是一种比赛,制作实物电脑鼠小车在迷宫找目标点,用时最短者获胜。考验参赛选手软硬件结合的能力。

2、走迷宫模拟软件中已实现功能

1、点击迷宫墙壁可编辑迷宫,并且可保存和加载迷宫形状文件;

2、自动搜索迷宫,采用回溯算法搜索整个迷宫;

3、采用洪水算法查找迷宫的最短路径。

整体界面

二、软件截图

打开迷宫形状配置文件

点击迷宫墙壁编辑迷宫形状

搜索迷宫

搜索迷宫

搜索迷宫,并且回溯未到过的地方

搜索结束,找到最短距离的路径

三、代码分享

代码中一共4个.py文件,一个迷宫形状配置文件,如下:

1、main.py

import tkinter as tk
import maze as maze
import micromouse as micromouse

root = tk.Tk()
windows_w = 640*2+100
windows_h = 640
bd = 10
map_size = 32
win = [15, 15]
root.title("MicroMouse")
root.geometry("{}x{}".format(windows_w, windows_h))


cv = tk.Canvas(root, width=windows_h*2, height=windows_h, bg='white')
cv.place(x=0, y=0)


mz = maze.Maze(cv, windows_h, bd, win, map_size)
mz.draw_maze()
mz.draw_win_point()

mouse = micromouse.MicroMouse(cv, mz.cell_len, bd, win, windows_h, map_size)
mouse.draw_mouse(0, 0)
mouse.draw_win_oval()
mouse.draw_search_maze()

save = tk.Button(root, text='保存迷宫', command=mz.save_maze, height=1, width=8)
save.place(x=windows_h*2+20, y=10)

open = tk.Button(root, text='加载迷宫', command=mz.load_maze, height=1, width=8)
open.place(x=windows_h*2+20, y=50)

search = tk.Button(root, text='探索迷宫', command=lambda mz=mz: mouse.search_maze(mz), height=1, width=8)
search.place(x=windows_h*2+20, y=90)

setmouse = tk.Button(root, text='重置电脑鼠', command=mouse.reset_mouse, height=1, width=8)
setmouse.place(x=windows_h*2+20, y=130)

root.mainloop()

2、tree.py



class Tree(object):

    def __init__(self):
        self.last_tree = None
        self.next_tree = None
        self.h = None
        self.w = None

3、maze.py

import numpy as np
from tkinter import filedialog


class Maze(object):

    def __init__(self, cv, windows_h, bd, win, map_size=32):
        self.map_size = map_size
        self.cv = cv
        self.bd = bd
        self.win = win
        self.up = 0
        self.down = 1
        self.left = 2
        self.right = 3
        self.maze_map = np.ones((map_size, map_size, 4), dtype='int8')  # h/y, w/x, wall/up,down,left,right
        self.cell_len = int((windows_h-2*self.bd)/map_size)
        self.line_hand = []
        self.win_point = None

    def draw_win_point(self):
        # clear win point
        if self.win_point is not None:
            self.cv.delete(self.win_point)
        # draw win point
        w, h = self.win
        x, y = (w+0.5)*self.cell_len+self.bd, (h+0.5)*self.cell_len+self.bd
        rate = self.cell_len/3
        x0, y0 = x - rate, y - rate
        x1, y1 = x + rate, y + rate
        self.win_point = self.cv.create_oval(x0, y0, x1, y1, fill='red')

    def draw_maze(self):
        # clear maze
        for tag in self.line_hand:
            self.cv.delete(tag)
        # draw maze
        for h in range(self.map_size):
            for w in range(self.map_size):
                for index in range(4):
                    # up and down for wall
                    if index in [self.up, self.down]:
                        x0, y0 = w*self.cell_len+self.bd, (h+index)*self.cell_len+self.bd
                        x1, y1 = (w+1)*self.cell_len+self.bd, (h+index)*self.cell_len+self.bd
                    # left and right for wall
                    else:
                        x0, y0 = (w+index-2)*self.cell_len+self.bd, h*self.cell_len+self.bd
                        x1, y1 = (w+index-2)*self.cell_len+self.bd, (h+1)*self.cell_len+self.bd
                    # no line draw white line
                    if self.maze_map[h, w, index] == 1:
                        color = 'black'
                    else:
                        color = 'Gainsboro'
                    # draw line
                    self.line_hand.append(self.cv.create_line(x0, y0, x1, y1, width=2, fill=color))
                    self.cv.tag_bind(self.line_hand[-1], '<Button-1>', lambda event, c=[h, w, index]: self.change_cell(c))

    def change_cell(self, c):
        # click to hide or show line
        h, w, index = c
        # edge wall
        if h == 0 and index == self.up:
            return
        if w == 0 and index == self.left:
            return
        # up wall
        if index == self.up:
            # deal clicked line
            if self.maze_map[h, w, self.up] == 1:
                self.maze_map[h, w, self.up] = 0
            else:
                self.maze_map[h, w, self.up] = 1
            # deal adjoin line
            if h-1 >= 0:
                if self.maze_map[h, w, self.up] == 0:
                    self.maze_map[h - 1, w, self.down] = 0
                else:
                    self.maze_map[h - 1, w, self.down] = 1
        # left wall
        if index == self.left:
            # deal clicked line
            if self.maze_map[h, w, self.left] == 1:
                self.maze_map[h, w, self.left] = 0
            else:
                self.maze_map[h, w, self.left] = 1
            # deal adjoin line
            if w-1 >= 0:
                if self.maze_map[h, w, self.left] == 0:
                    self.maze_map[h, w - 1, self.right] = 0
                else:
                    self.maze_map[h, w - 1, self.right] = 1
        self.draw_maze()

    def save_maze(self):
        fileSave = filedialog.asksaveasfilename(defaultextension='.txt', filetypes=[("txt files", ".txt")])
        np.savetxt(fileSave, self.maze_map.reshape((1, self.map_size*self.map_size*4)), fmt='%d')

    def load_maze(self):
        filePath = filedialog.askopenfilename()
        self.maze_map = np.loadtxt(filePath).reshape((self.map_size, self.map_size, 4))
        self.draw_maze()

    def get_maze_map(self):
        return self.maze_map.copy()


4、micromouse.py

import numpy as np
from tkinter import filedialog


class Maze(object):

    def __init__(self, cv, windows_h, bd, win, map_size=32):
        self.map_size = map_size
        self.cv = cv
        self.bd = bd
        self.win = win
        self.up = 0
        self.down = 1
        self.left = 2
        self.right = 3
        self.maze_map = np.ones((map_size, map_size, 4), dtype='int8')  # h/y, w/x, wall/up,down,left,right
        self.cell_len = int((windows_h-2*self.bd)/map_size)
        self.line_hand = []
        self.win_point = None

    def draw_win_point(self):
        # clear win point
        if self.win_point is not None:
            self.cv.delete(self.win_point)
        # draw win point
        w, h = self.win
        x, y = (w+0.5)*self.cell_len+self.bd, (h+0.5)*self.cell_len+self.bd
        rate = self.cell_len/3
        x0, y0 = x - rate, y - rate
        x1, y1 = x + rate, y + rate
        self.win_point = self.cv.create_oval(x0, y0, x1, y1, fill='red')

    def draw_maze(self):
        # clear maze
        for tag in self.line_hand:
            self.cv.delete(tag)
        # draw maze
        for h in range(self.map_size):
            for w in range(self.map_size):
                for index in range(4):
                    # up and down for wall
                    if index in [self.up, self.down]:
                        x0, y0 = w*self.cell_len+self.bd, (h+index)*self.cell_len+self.bd
                        x1, y1 = (w+1)*self.cell_len+self.bd, (h+index)*self.cell_len+self.bd
                    # left and right for wall
                    else:
                        x0, y0 = (w+index-2)*self.cell_len+self.bd, h*self.cell_len+self.bd
                        x1, y1 = (w+index-2)*self.cell_len+self.bd, (h+1)*self.cell_len+self.bd
                    # no line draw white line
                    if self.maze_map[h, w, index] == 1:
                        color = 'black'
                    else:
                        color = 'Gainsboro'
                    # draw line
                    self.line_hand.append(self.cv.create_line(x0, y0, x1, y1, width=2, fill=color))
                    self.cv.tag_bind(self.line_hand[-1], '<Button-1>', lambda event, c=[h, w, index]: self.change_cell(c))

    def change_cell(self, c):
        # click to hide or show line
        h, w, index = c
        # edge wall
        if h == 0 and index == self.up:
            return
        if w == 0 and index == self.left:
            return
        # up wall
        if index == self.up:
            # deal clicked line
            if self.maze_map[h, w, self.up] == 1:
                self.maze_map[h, w, self.up] = 0
            else:
                self.maze_map[h, w, self.up] = 1
            # deal adjoin line
            if h-1 >= 0:
                if self.maze_map[h, w, self.up] == 0:
                    self.maze_map[h - 1, w, self.down] = 0
                else:
                    self.maze_map[h - 1, w, self.down] = 1
        # left wall
        if index == self.left:
            # deal clicked line
            if self.maze_map[h, w, self.left] == 1:
                self.maze_map[h, w, self.left] = 0
            else:
                self.maze_map[h, w, self.left] = 1
            # deal adjoin line
            if w-1 >= 0:
                if self.maze_map[h, w, self.left] == 0:
                    self.maze_map[h, w - 1, self.right] = 0
                else:
                    self.maze_map[h, w - 1, self.right] = 1
        self.draw_maze()

    def save_maze(self):
        fileSave = filedialog.asksaveasfilename(defaultextension='.txt', filetypes=[("txt files", ".txt")])
        np.savetxt(fileSave, self.maze_map.reshape((1, self.map_size*self.map_size*4)), fmt='%d')

    def load_maze(self):
        filePath = filedialog.askopenfilename()
        self.maze_map = np.loadtxt(filePath).reshape((self.map_size, self.map_size, 4))
        self.draw_maze()

    def get_maze_map(self):
        return self.maze_map.copy()


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

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

相关文章

即时通讯平台项目测试(主页面)

http://8.130.98.211:8080/login.html项目访问地址&#xff1a;即时通讯平台http://8.130.98.211:8080/login.html 本篇文章进行项目主页面的测试。 在测试前需要先对待测内容进行分类&#xff0c;按照功能进行分类可以分为&#xff1a;个人信息设置、发送/接收消息、添加好友…

YOLO V8-Pose 【批量图片推理】 推理详解及部署实现

前言 在实际处理过程中&#xff0c;我们使用YOLO V8进行推理时&#xff0c;通常会针对一张图片进行推理。如果需要对多张图片进行推理&#xff0c;则可以通过一个循环来实现对图片逐张进行推理。 单张图片推理时&#xff0c;需要注意图片的尺寸必须是32的倍数&#xff0c;否则…

游戏AI的创造思路-技术基础-情感计算(1)

游戏中的AI也是可以和你打情感牌的哦&#xff0c;不要以为NPC是没有感情的&#xff0c;不过&#xff0c;不要和NPC打过多的情感牌&#xff0c;你会深陷其中无法自拔的~~~~~~ 目录 1. 情感计算算法定义 2. 发展历史 3. 公式和函数 3.1. 特征提取阶段 TF-IDF&#xff08;词频…

算法学习笔记(8.1)-动态规划入门

目录 问题特性&#xff1a; 最优子结构&#xff1a; 代码示例&#xff1a;&#xff08;动态规划最优子结构&#xff09; 上述最小代价爬楼梯的运行过程&#xff1a; 代码示例&#xff1a; 无后效性&#xff1a; 解析&#xff1a; 具体过程图示如下&#xff1a; 具体的…

算法的复杂度

文章目录 一、算法的效率1、复杂度的概念2、复杂度的重要性 二、时间复杂度三、空间复杂度四、大O的渐进表示发五、计算复杂度案例1、计算Func1函数的复杂度2、计算Fun2的时间复杂度3、计算Func3的时间复杂度4、计算Func4的时间复杂度5、计算strchr的时间复杂度6、计算Func5的时…

解决Invalid or unsupported by client SCRAM mechanisms(dbeaver)

在用工具&#xff08;dbeaver&#xff09;链接Opengauss数据库的时候&#xff0c;报出标题的错误。原因为驱动不正确。 驱动下载地址&#xff1a;https://opengauss.org/zh/download/ 下载完的包 &#xff0c;解压后&#xff0c;里面应该有两个jar 包,使用postgresql.jar dbe…

MT3056 交换序列

思路&#xff1a; 与题目 MT3055 交换排列 类似 代码&#xff1a; #include <bits/stdc.h> using namespace std; const int N 1e4 10; int n, fa[N], b[N], d[N]; void init(int n) {for (int i 1; i < n; i)fa[i] i; } int find(int x) {return x fa[x] ?…

WebRTC批量发送消息API接口的特性有哪些?

WebRTC批量发送消息api接口怎么样&#xff1f;接口性能怎么用&#xff1f; WebRTC技术允许浏览器和移动应用进行实时通信。通过WebRTC&#xff0c;开发者可以构建视频、语音、数据共享等应用。AokSend将重点探讨WebRTC批量发送消息API接口的特性。 WebRTC批量发送消息API接口…

Qt/QML学习-PathView

QML学习 PathView例程视频讲解代码 main.qml import QtQuick 2.15 import QtQuick.Window 2.15Window {width: 640height: 480visible: truetitle: qsTr("Hello World")color: "black"PathView {id: pathViewanchors.fill: parentmodel: ListModel {List…

[Spring] SpringBoot基本配置与快速上手

&#x1f338;个人主页:https://blog.csdn.net/2301_80050796?spm1000.2115.3001.5343 &#x1f3f5;️热门专栏: &#x1f9ca; Java基本语法(97平均质量分)https://blog.csdn.net/2301_80050796/category_12615970.html?spm1001.2014.3001.5482 &#x1f355; Collection与…

AJAX-个人版2.0

AJAX&#xff08;Asynchronous Javascript And Xml&#xff09; 传统请求及缺点 传统的请求都有哪些&#xff1f; 直接在浏览器地址栏上输入URL。点击超链接提交form表单使用JS代码发送请求 window.open(url)document.location.href urlwindow.location.href url… 传统请…

面试总结-基础js

一、变量提升&#xff08;函数里面先形参赋值&#xff0c;再变量提升&#xff0c;最后执行代码&#xff09; 1、概念&#xff1a;当浏览器开辟出供代码执行的栈内存后&#xff0c;代码并没有自上而下立即执行&#xff0c;而是继续做了一些事情&#xff0c;把当前作用域所有带v…

C++基础编程100题-021 OpenJudge-1.4-01 判断数正负

更多资源请关注纽扣编程微信公众号 http://noi.openjudge.cn/ch0104/01/ 描述 给定一个整数N&#xff0c;判断其正负。 输入 一个整数N(-109 < N < 109) 输出 如果N > 0, 输出positive; 如果N 0, 输出zero; 如果N < 0, 输出negative 样例输入 1样例输出…

【Linux】命令执行的判断依据:;,,||

在某些情况下&#xff0c;很多命令我想要一次输入去执行&#xff0c;而不想要分次执行时&#xff0c;该如何是好&#xff1f; 基本上有两个选择&#xff0c; 一个是通过shell脚本脚本去执行&#xff0c;一种则是通过下面的介绍来一次入多个命令。 1.cmd&#xff1a;cmd&#…

SAP EWM display message对话框长度限制

1.问题 使用标准方法/scwm/cl_rf_dynpro_srvc=>display_message显示消息文本,由于消息文本过长而被截取,影响显示效果 2.解决 通过调试跟踪当前标准方法,发现屏幕显示长度为40,最多显示4行,且iv_msg_text把每一行显示字段用空格拼接起来,故以下代码需要把显示消息…

Unity 打包的安卓APK在模拟器运行一会卡死

Unity 安卓APK模拟器运行一会卡死 如题&#xff0c;unity在模拟器上运行安卓apk挂机一会就卡死&#xff0c;在真机上没问题。因为打包时勾选了这个帧率优化选项&#xff0c;2019.2之后的功能&#xff0c;最坑的时打包时默认勾选&#xff0c;所以使用这个版本打包时&#xff0c…

如何写好品牌宣传稿提升品牌曝光?看这篇文章就够了

在这个信息爆炸的时代&#xff0c;一句精炼而富有力量的宣传语&#xff0c;足以让品牌在万千竞争者中脱颖而出。撰写一篇成功的品牌宣传稿&#xff0c;不仅是对文字艺术的驾驭&#xff0c;也是对品牌灵魂的深刻洞察与精准传达&#xff0c;更是连接品牌与消费者情感与认知的桥梁…

和鲸101计划夏令营火热进行中!北中医助阵医学数据探索

上周&#xff0c;和鲸社区 2024 夏令营已经正式开营&#xff01; 从 2021 年开始&#xff0c;和鲸社区在每年暑假期间都会为大家提供集中化、系统化的数据科学相关的技能实践和培训&#xff0c;每年都有几千名同学借此机会积累宝贵的实战经验&#xff0c;丰富个人简历作品&…

Apache功能配置:访问控制、日志分割; 部署AWStats日志分析工具

目录 保持连接 访问控制 只允许指定ip访问 拒绝指定主机其他正常访问 用户授权 日志格式 日志分割 操作步骤 使用第三方工具cronolog分割日志 AWStats日志分析 操作步骤 访问AwStats分析系统 保持连接 Apache通过设置配置文件httpd-default.conf中相关的连接保持参…

Docker安装HomeAssistant

检查Docker服务是否正常运行&#xff0c;确保Docker正常运行。 systemctl status docker#输出---------------------- docker.service - Docker Application Container EngineLoaded: loaded (/usr/lib/systemd/system/docker.service; enabled; vendor preset: disabled)Activ…