2019美赛D题,元胞自动机模拟游客疏散过程

这篇博客记录了作者参加2019年美国大学生数学建模比赛时,使用元胞自动机模拟游客疏散的过程。由于缺乏卢浮宫的建筑平面图,他们构建了自己的模型并设定了一些简化假设。文章分享了团队的想法,如人员移动分析和安全出口的考虑,并展示了部分代码实现,但指出仅完成了出口朝东的编程,且在出口方向逻辑设计上有待改进。
摘要由CSDN通过智能技术生成

2019美赛D题人员疏散模拟(错误解答,仅记录)

2021年3月21号编辑内容

特此说明:笔主写这篇文章的时候还是大三上学期结束,认知、技术都完全不过关,此时再回看这篇文章,着实有很多问题,甚至是误导。特此说明
笔主从学习Python,也就是写下这篇文章的时期,目前从事前端开发工作,也开始学习C++,也没有那种机会进入相关算法研发工作。今时看来,此文的编码、思想都略显幼稚甚至荒唐。
毕竟是自己踩下的脚印,不忍抹去,此段话放在开头,希望刷到的同学谨慎参考,谢谢各位。
———————————————————————————————————————————

有幸参加了2019年美国大学生数学建模比赛。比赛过程中担任的角色中有编程任务,现将当时的代码和大家分享。比赛结束后抽空将代码完善了一下,仍然有诸多不足之处。

一、我们团队的想法

我们团队怎么也找不到卢浮宫的建筑平面图,有找到的吗????不能精确定位模拟,所以就基于疏散问题建立了自己的平面图。
1、假设(部分)
(1)场馆内无障碍物(这样简化了很多)
(2)场馆内人员单位时间内最多能移动一个元胞距离(很关键,不然非常)
2、馆内人员移动分析
在这里插入图片描述
即单位时间内可以移动八个方向,每次一个元胞距离
3、安全出口数量以及安全出口的考虑
如果考虑多个安全出口,仅仅比赛那点时间,我这点水平编程是不够的,所以指定只有一个安全出口;在考虑安全出口位置的时候,我们也指定出口位置为墙上的一个开口,比赛结束后,我将代码优化补全,现在支持安全出口的位置在室内任何地方。

二、代码部分

因为不是一篇写这次比赛解决方法的博客,下面我重点展示代码实现。先展示各个点的实现,最后在附送上完整代码。
运用到matplotlib库进行可视化,所以就不提基础部分,主要展示怎么将现实问题抽象成代码
1、创建房间、创建人员及初始位置生成、安全出口

N, row, column = 250, 20, 20  #室内人数,矩阵的行数,矩阵的列数
room = np.zeros((row + 2, column + 2))  # 创建房间
export = [(6, 11, 'E')]  # 设定出口位置和开门方向,此处为坐标轴坐标

** 注意:**出口的坐标表示为二维直角坐标系的定位方式,并非出口在矩阵中的索引,出口方向分别为‘N’‘S’‘W’‘E’,对应四个方位。

def initial_room():
    '''
    生成初始人员并进行随机分配
    '''
    coordinates = []  # 室内人员坐标
    for i in range(N):
        generated_data = [random.randint(1, row), random.randint(1, column)]
        if not generated_data in coordinates:  # 去掉重复数据
            coordinates.append(generated_data)
    for i in range(len(coordinates)):
        room[coordinates[i][0]][coordinates[i][1]] = 1
    # 创建围墙、创建出口
    for i in range(len(room)):
        for j in range(len(room)):
            if i == 0 or i == len(room) - 1 or j == 0 or j == len(room[i]) - 1:
                room[i][j] = 9
    for i in range(len(export)):
        room[export[i][1]][export[i][0]] = 8
    return

人员随机分配,对应矩阵中的索引,设置删除重复的位置,即得一个人对应一个位置。围墙使用数值9表示,出口使用数值8表示。
2、可视化

for i in range(1, len(room) - 1):
    for j in range(1, len(room[i]) - 1):
        if room[i][j] == 1:
           rect = mpathes.Circle((j + 0.5, i + 0.5), 0.3, color='grey')
                ax.add_patch(rect)
plt.show()

将矩阵索引与二维坐标Y轴一一对应,即矩阵索引为0的列表对应坐标轴Y方向最小的坐标,便于后续编程
在这里插入图片描述

完整代码

代码半完整写下来将近300行,还有一些没有完善,下文会提到

import matplotlib.pyplot as plt
import matplotlib.patches as mpathes
import numpy as np
import random


# 初始位置生成
def initial_room():
    '''
    生成初始人员并进行随机分配
    '''
    coordinates = []  # 室内人员坐标
    for i in range(N):
        generated_data = [random.randint(1, row), random.randint(1, column)]
        if not generated_data in coordinates:  # 去掉重复数据
            coordinates.append(generated_data)
    for i in range(len(coordinates)):
        room[coordinates[i][0]][coordinates[i][1]] = 1
    # 创建围墙、创建出口
    for i in range(len(room)):
        for j in range(len(room)):
            if i == 0 or i == len(room) - 1 or j == 0 or j == len(room[i]) - 1:
                room[i][j] = 9
    for i in range(len(export)):
        room[export[i][1]][export[i][0]] = 8
    return


# 创建平台
def create_flat():
    # fig, ax = plt.subplots()
    plt.xticks(np.arange(0, column + 3, 1.0))
    plt.yticks(np.arange(0, row + 3, 1.0))
    plt.grid(linestyle='--')
    wall_botton = mpathes.Rectangle((0, 0), column + 2, 1, color='grey')
    wall_left = mpathes.Rectangle((0, 0), 1, row + 2, color='grey')
    wall_top = mpathes.Rectangle((0, row + 1), column + 2, 1, color='grey')
    wall_right = mpathes.Rectangle
  • 21
    点赞
  • 122
    收藏
    觉得还不错? 一键收藏
  • 10
    评论
评论 10
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值