matplotlib绘制位置-时序甘特图

news2024/11/27 4:15:11

文章目录

  • 1 前言
  • 2 知识点
    • 2.1 matplotlib.pyplot.barh
    • 2.2 matplotlib.legend的handles参数
  • 3 代码实现
  • 4 绘制效果
  • 5 总结
  • 参考

1 前言

这篇文章的目的是,总结记录一次使用matplotlib绘制时序甘特图的经历。之所以要绘制这个时序甘特图,是因为22年数模研赛C题需要用到,用于更好地呈现求解的车身缓冲区调序优化结果。
首先,我们觉得在这篇博客中出现的下面这张图展示效果很好,于是也想绘制一张。

这张图中,横坐标是递增变化的时间,纵坐标是PBS中的区域编号,其中不同的颜色代表不同的车身,如果某个时间段车身达到了某个区域,那么图中所对应的矩形区块将填充为该车身对应的颜色。
在知道上述信息后,我们开始在网上查找甘特图的绘制方法,因为我个人习惯用python的matplotlib库绘制图表,于是根据关键词搜索到了如下的文章: Python实现生产过程可视化(甘特图)。看着比较像我们想要的那种效果,于是琢磨了一下代码怎么写的。

2 知识点

拜读完代码后,我总结了使用matplotlib绘制甘特图的一些知识点。

2.1 matplotlib.pyplot.barh

该函数的作用是绘制横向的柱状图。
官方文档函数定义如下:
matplotlib.pyplot.barh(y, width, height=0.8, left=None, *, align='center', data=None, **kwargs)
使用到的参数详解:

参数名称解释
y可传入float类型,决定柱状图的y轴坐标
width可传入float类型,决定柱状图的宽带(可以理解为横跨x轴的长度)
height可传入float类型,默认0.8,决定柱状图的高度(可以理解为横跨y轴的长度)
left可传入float类型,默认0,决定柱状图最左侧与y轴的距离
align可选’center’或’edge’, 默认 ‘center’,柱状图与y坐标的对齐方式,默认居中
color柱状图的颜色
edgecolor柱状图边缘的颜色
linewidth柱状图边缘的宽度,如果为0则不绘制边缘
zorderfloat类型,控制artist对象的绘制顺序,zorder越小越先绘制(有点图层的意思)

2.2 matplotlib.legend的handles参数

我也是第一次见往plt.legend函数中传入handles参数的(没有系统学过matplotlib库😭),这里也不详细解释了,直接说怎么用吧。当我们想要自定义图例时,使用下面代码:

patches = [mpatches.Patch(color = m_colors[i], label = m_labels[i]) for i in range(m)]
plt.legend(handles = patches)

其中,color参数是图例(matplotlib.patches对象)对应的颜色,label为图例对应的标签。

3 代码实现

绘制代码如下:

import numpy as np
import matplotlib.pyplot as plt
import matplotlib.patches as mpatches

plt.rcParams['font.sans-serif'] = ['SimHei']  # 用来正常显示中文标签
plt.rcParams['axes.unicode_minus'] = False  # 用来正常显示负号

def gantt_chart(wt, x_labels, y_labels, m_labels):
    """
    wt: 工作矩阵,大小为mxnx2,m为车身数,n为区域编号数,第三维中
        第1个元素为车身进入区域的时间,第2个元素为停留时间。
    color_list:代表各车身的颜色矩阵,大小为nx4。
    """
    m, n = wt.shape[0], wt.shape[1]
    m_colors = plt.colormaps['terrain'](np.linspace(0, 0.95, m))
    for i in range(n):
        for j in range(m):
            if wt[j, i, 1] != 0:
                plt.barh(y = i, width = wt[j, i, 1], left = wt[j, i, 0], height = 1, edgecolor = (0, 0, 0),
                         color = m_colors[j], zorder = 10)

    # 图例绘制
    patches = [mpatches.Patch(color = m_colors[i], label = m_labels[i]) for i in range(m)]
    plt.legend(handles = patches, bbox_to_anchor = (1.005, 0), loc = 3, borderaxespad = 0)
    plt.xticks(x_labels, fontsize = 7)
    plt.yticks(list(range(n)), y_labels)
    plt.xlabel("时间/s")
    plt.ylabel("区域编号")
    plt.title('车身位置-时序甘特图')
    plt.grid(axis = 'x', zorder = 0)
    # plt.savefig('result21_车身位置-时序甘特图.jpg', dpi = 200)
    plt.show()

def custom_gantt_chart(path = 'result21.csv', car_num = 25, T = 180):
    data = np.loadtxt(open(path, "rb"), delimiter = ",", encoding = 'utf-8-sig', dtype = object)[1:car_num + 1, 1:T + 1]
    car_label = [f'car{i}' for i in range(1, 26)]
    region_code = ['1', '410', '49', '48', '47', '46', '45', '44', '43', '42', '41',
                   '310', '39', '38', '37', '36', '35', '34', '33', '32', '31',
                   '210', '29', '28', '27', '26', '25', '24', '23', '22', '21', '2']
    car_num, T_num, region_num = data.shape[0], data.shape[1], len(region_code)
    T_range = [t for t in range(0, T_num + 1, 3)]
    Wt = np.zeros((car_num, region_num, 2))
    Wt[:, :, 0] = -1
    for i in range(car_num):
        for j in range(T_num):
            if data[i, j] == '' or data[i, j] == '3':
                continue
            idx = region_code.index(data[i, j])
            if Wt[i, idx, 0] == -1:
                Wt[i, idx, 0] = j
            Wt[i, idx, 1] += 1

    gantt_chart(Wt, T_range, region_code, car_label)


if __name__ == '__main__':
    custom_gantt_chart('result21.csv', car_num = 25, T = 200)

4 绘制效果

在这里插入图片描述

5 总结

可以从绘制效果中看到,有些柱状图的颜色两两之间不仔细看根本分不出来。对于这个问题,主要是这条代码m_colors = plt.colormaps['terrain'](np.linspace(0, 0.95, m))在色条上均匀取色时,因为色条颜色数量太少(即使是渐变色条,随着取色数量增多也不容易分辨)造成的。terrain颜色条包含的颜色如下图:

关于更多的颜色条种类及使用方法参见:https://matplotlib.org/stable/tutorials/colors/colormaps.html

参考

[1] https://zhuanlan.zhihu.com/p/106787569
[2] https://matplotlib.org/stable/api/_as_gen/matplotlib.pyplot.barh.html
[3] https://matplotlib.org/stable/api/legend_api.html
[4] https://matplotlib.org/stable/tutorials/colors/colormaps.html

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

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

相关文章

关于consul的下载方法

linux下 sudo yum install -y yum-utils sudo yum-config-manager --add-repo https://rpm.releases.hashicorp.com/RHEL/hashicorp.repo sudo yum -y install consulwindow下 https://developer.hashicorp.com/consul/downloads 然后把里面的exe文件放在gopath下就行了 验证…

手机照片误删怎么办,电脑照片误删怎么办怎么才能找回,EasyRecovery来帮您

手机照片误删怎么办,电脑照片误删怎么办怎么才能找回,EasyRecovery 2023来帮您!!! EasyRecovery 2023是一款操作安全、价格便宜、用户自主操作的 数据恢复 方案,它支持从各种各样的 存储介质 恢复删除 或者…

12 注册登录

12 注册登录 整体概述 使用数据库连接池实现服务器访问数据库的功能,使用POST请求完成注册和登录的校验工作。 本文内容 介绍同步实现注册登录功能,具体涉及到流程图、载入数据库表、提取用户名和密码、注册登录流程与页面跳转的代码实现。 流程图&a…

加了ComponentScan,但是feign接口无法注入的原因

正文 正确的注入 如果发现无法注入:看看启动类Application是否有加入注解:EnableFeignClients(AppConstant.BASE_PACKAGES) 注意:EnableFeignClients和ComponentScan是两个独立的扫描,所以,如果只配置了ComponentSca…

FPGA控制RGB灯WS2812B

文章目录 FPGA控制RGB灯WS2812B1、简介1.1水一水1.2程序完成目标1.3项目工程结构 2、代码3、仿真代码4、结果展示 FPGA控制RGB灯WS2812B 1、简介 1.1水一水 最近在学习WS2812B手册,是一个简单的协议编写,做的时间也算是比较久,相对做出了一…

00-认识C++

2、认识C 2.1、例子 一个简单的C例子 #include <iostream>int main() {using namespace std; //使用名称空间cout << "Com up and C me some time.";cout << endl; //换行符&#xff0c;还可以cout<<"\n";cout <…

【JAVA】集合(Collection、Map)

集合和数组都是容器 数组&#xff1a;类型确定&#xff0c;长度固定&#xff0c;可以存储基本类型和引用类型的数据 集合&#xff1a;类型可以不固定&#xff0c;大小可变&#xff0c;只能存储引用数据类型的数据 Collection单列单列集合&#xff0c;每个元素只包含一个值Ma…

伴随矩阵的特征值跟原矩阵特征值居然有关系!!!附证明

文章目录 论点&#xff1a;A与其伴随矩阵的特征值相乘等于|A|证明证明证明中涉及的相关定理&#xff1a;1.逆矩阵与伴随矩阵的关系2.A可逆时&#xff0c;A的逆矩阵的特征值是原矩阵特征值的倒数 论点&#xff1a;A与其伴随矩阵的特征值相乘等于|A| 证明 证明 证明中涉及的相关…

html css实现爱心

<!DOCTYPE html> <html lang"en"> <head><meta charset"UTF-8"><meta name"viewport" content"widthdevice-width, initial-scale1.0"><title>Document</title><style>/* 爱心 */.lo…

基于Matlab实现小偷体貌识别仿真(附上源码+数据集)

小偷体貌识别是一种应用于安全领域的重要技术&#xff0c;它利用计算机视觉和机器学习的方法&#xff0c;通过对监控视频中的人体特征进行提取和分析&#xff0c;来识别出可能的小偷。在本文中&#xff0c;我们将介绍如何使用Matlab实现小偷体貌识别的仿真。 文章目录 介绍部分…

测牛学堂:软件测试工程师都要懂的软件开发模型总结

软件开发模型之快速原型 之前跟大家介绍了最早期的瀑布模型。今天聊一下快速原型模型。 快速原型&#xff0c;在初步确定用户需求之后&#xff0c;快速构造出一个原型项目&#xff0c;可以跟用户展示软件的功能&#xff0c;用户根据原型进行评审&#xff0c;提出更进一步的细…

JavaWeb-Servlet服务连接器(终)

上一篇文章JavaWeb-Servlet服务连接器&#xff08;三&#xff09;_Alphamilk的博客-CSDN博客 目录 1.ServletContext通信 会话技术Cookie与Session 1.Cookie 2.Session 1.ServletContext通信 概念&#xff1a;代表了整个web应用&#xff0c;用于与服务器实现通信 可以通…

6.2 口令破解攻击

数据参考&#xff1a;CISP官方 目录 口令安全问题口令破解攻击口令破解安全防护口令使用安全管理 一、口令安全问题 什么是口令 身份验证的机制&#xff0c;俗称 “密码"&#xff0c;对应英文单词为 password成本较低&#xff0c;得到广泛应用信息安全中的 “密码”…

基于 Nginx All In One 的 Outline Wiki 部署方法

1. Outline 简介 官网&#xff1a;https://www.getoutline.com/ Outline 是一个开源的知识库和团队协作工具&#x1f9e0;&#xff0c;旨在帮助团队共享、组织和协作文档&#x1f4dd;。它提供了一个简洁的界面&#xff0c;使用户能够轻松创建、编辑和查看文档。 以下是 Out…

sudo免密码设置以及设置失败解决方法

使用sudo visudo修改\etc\sudoers文件 打开后有很多已有的设置大致格式username ALL(ALL:ALL) ALL&#xff0c;都不要动&#xff01; 在文件结尾加上一句话&#xff1a; username ALL(ALL:ALL) NOPASSWD: ALLusername就是目前你这个账户的名字&#xff0c;开机时会输密码登录…

Nginx访问日志及巡检统计

一、前言 二、词汇解释 2.1、pv和uv的区别 PV&#xff08;Page View访问量/也卖弄浏览数&#xff09;&#xff1a;指在一定统计周期内&#xff0c;用户每次刷新网页一次即计算一次。PV高不一定代表来访者多:PV与来访者的数量成正比&#xff0c;但是PV并不直接决定页面的真实来…

同样的字符串,有一些事长度为3,有一些长度为2,导致Convert.ToByte(macStringArray[i], 16);出错

同样的字符串&#xff0c;有一些事长度为3&#xff0c;有一些长度为2,导致Convert.ToByte(macStringArray[i], 16);出错。 最后&#xff0c;把长度为2的复制过去&#xff0c;就好了。 要复制“1C- 只复制1C不行 { “pc101”:“1C-69-7A-BD-05-C4”, “pc102”:“1C-69-7A-BD…

Selenium自动化测试实战之自动化测试基础

自动化测试概念 是把以人为驱动的测试转化为机器执行的一种过程&#xff0c;它是一种以程序测试程序的过程。 自动化只是测试方式&#xff0c;跟测试阶段无关。 可以把任何测试工作写一个程序自动化实现都可以称为自动化测试。 selenium自动化测试&#xff1a;2023最新的Sele…

docker可视化工具Portainer

1:Portainer简介 Portainer是一个docker可视化管理工具&#xff0c;可以非常方便地管理docker镜像容器。官网地址&#xff1a;https://www.portainer.io/ 注&#xff1a;现在Portainer有BE&#xff08;收费&#xff09;和CE&#xff08;免费&#xff09;版本&#xff0c;安装的…

答疑:Arduino IDE配置其他开发板下载速度慢

基于案例&#xff1a;Linux环境Arduino IDE中配置ATOM S3 通常&#xff0c;网络问题较多&#xff0c;可以使用一些技巧。 https://m5stack.oss-cn-shenzhen.aliyuncs.com/resource/arduino/package_m5stack_index.json 没有配置&#xff0c;不支持M5Stack&#xff08;ESP32&…