matplotlib从起点出发(8)_Tutorial_8_Legend

news2024/10/10 14:30:26

1 图例教程

在matplotlib中灵活地生成Legend。

本图例指南是legend()中可用文档的扩展——在继续阅读本指南之前,请确保你熟悉legend()文档的内容。

本指南使用了一些常用术语,为清楚起见,此处记录了这些术语:

  • legend entry
    图例由一个或多个图例entry(条目)组成。entry(条目)仅由一个键和一个标签组成。

  • legend key
    每个图例标签左侧的彩色/图案标记。

  • legend label
    描述由键表示的句柄的文本。

  • legend handle
    用于在图例中生成相应条目的原始对象。

2 控制图例的条目

调用不带参数的legend()会自动获取图例句柄及其关联的标签。此功能等效于:

handles, labels = ax.get_legend_handles_labels()
ax.legend(handles, labels)

get_legend_handles_labels()函数返回轴上存在的句柄/artist列表,可用于为生成的图例生成条目——值得注意的是,并非所有的artist都可以添加到图例中,此时必须创建一个“代理”(请参阅创建专门用于添加到图例的artist,又名代理artist,以获取更多详细信息。)

注意
将忽略以空字符串作为标签或标签以下划线“_”开头的artist。

为了完全控制要添加到图例的内容,通常将适当的句柄直接传递给legend():

fig, ax = plt.subplots()
line_up, = ax.plot([1, 2, 3], label='Line 2')
line_down, = ax.plot([3, 2, 1], label='Line 1')
ax.legend(handles=[line_up, line_down])

在某些情况下,无法设置句柄的标签,因此可以将标签列表传递给legend()

fig, ax = plt.subplots()
line_up, = ax.plot([1, 2, 3], label='Line 2')
line_down, = ax.plot([3, 2, 1], label='Line 1')
ax.legend([line_up, line_down], ['Line Up', 'Line Down'])

3 创建专门用于添加到legend的artist(代理artist)

并非所有句柄都可以自动转换为图例条目,因此通常需要创建一个可以的artist。图例句柄不必存在于Figure或Axes上即可使用。

假设我们想创建一个图例,其中包含一些由红色表示的数据条目:

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

fig, ax = plt.subplots()
red_patch = mpatches.Patch(color='red', label='The red data')
ax.legend(handles=[red_patch])

plt.show()

在这里插入图片描述

有许多受支持的图例句柄。我们可以创建一条带有标记的线,而不是创建色块:

import matplotlib.lines as mlines

fig, ax = plt.subplots()
blue_line = mlines.Line2D([], [], color='blue', marker='*',
                          markersize=15, label='Blue stars')
ax.legend(handles=[blue_line])

plt.show()

在这里插入图片描述

如图,图例换成了一条带有蓝色星星的线。

3 图例位置

图例的位置可以通过关键字参数loc进行指定。有关更多详细信息,请参阅legend()中的文档。

bbox_to_anchor关键字为手动图例放置提供了很大程度的控制。例如,如果你希望axes图例位于图形的右上角而不是axes的角,只需指定角的位置和该位置的坐标系:

ax.legend(bbox_to_anchor=(1, 1),
          bbox_transform=fig.transFigure)

自定义图例放置的更多示例:

fig, ax_dict = plt.subplot_mosaic([['top', 'top'], ['bottom', 'BLANK']],
                                  empty_sentinel="BLANK")
ax_dict['top'].plot([1, 2, 3], label="test1")
ax_dict['top'].plot([3, 2, 1], label="test2")
# Place a legend above this subplot, expanding itself to
# fully use the given bounding box.
ax_dict['top'].legend(bbox_to_anchor=(0., 1.02, 1., .102), loc='lower left',
                      ncols=2, mode="expand", borderaxespad=0.)

ax_dict['bottom'].plot([1, 2, 3], label="test1")
ax_dict['bottom'].plot([3, 2, 1], label="test2")
# Place a legend to the right of this smaller subplot.
ax_dict['bottom'].legend(bbox_to_anchor=(1.05, 1),
                         loc='upper left', borderaxespad=0.)

在这里插入图片描述

Figure的图例

有时,相对于(子)图形而不是单个Axes来放置图例会更有意义。通过使用constrained_layout并在loc关键字参数的开头指定外部,图例将绘制在(子)图的Axes区域之外。

fig, axs = plt.subplot_mosaic([['left', 'right']], layout='constrained')

axs['left'].plot([1, 2, 3], label="test1")
axs['left'].plot([3, 2, 1], label="test2")

axs['right'].plot([1, 2, 3], 'C2', label="test3")
axs['right'].plot([3, 2, 1], 'C3', label="test4")
# Place a legend to the right of this smaller subplot.
fig.legend(loc='outside upper right')

在这里插入图片描述

这里接收的语法与普通loc关键字略有不同,其中“外右上”与“外上右”不同。
在这里插入图片描述

在这里插入图片描述

4 同一Axes上的多个图例

有时,将图例条目拆分到 多个图例中会更清晰。虽然这样做的一个基本方法可能是多次调用legend()函数,但你会发现Axes上只存在一个图例。这样做是为了可以重复调用legend()以将图例更新到 Axes上的最新句柄。要保留旧的图例实例,我们必须手动将它们添加到 Axes 中:

fig, ax = plt.subplots()
line1, = ax.plot([1, 2, 3], label="Line 1", linestyle='--')
line2, = ax.plot([3, 2, 1], label="Line 2", linewidth=4)

# Create a legend for the first line.
first_legend = ax.legend(handles=[line1], loc='upper right')

# Add the legend manually to the Axes.
ax.add_artist(first_legend)

# Create another legend for the second line.
ax.legend(handles=[line2], loc='lower right')

plt.show()

在这里插入图片描述

5 图例句柄

为了创建图例条目,句柄作为参数提供给相应的HandlerBase子类。处理程序子类的选择由以下规则确定:

  1. 使用handler_map关键字中的值更新get_legend_handler_map();
  2. 检查句柄是否在新创建的handler_map中;
  3. 检查句柄的类型是否在新创建的handler_map中;
  4. 检查句柄的mro中的任何类型是否位于新创建的handler_map中。

为了完整起见,此逻辑主要在get_legend_handler()中实现。

所有这些灵活性意味着我们有必要的钩子来为我们自己的图例键类型实现自定义处理程序。

使用自定义处理程序的最简单示例是实例化现有legend_handler之一。处理程序库子类。为了简单起见,让我们选择legend_handlerHandlerLine2D接受numpoints参数(为了方便起见,numpoints也是legend()函数上的关键字)。然后,我们可以将实例到Handler的映射作为图例的关键字传递。

from matplotlib.legend_handler import HandlerLine2D

fig, ax = plt.subplots()
line1, = ax.plot([3, 2, 1], marker='o', label='Line 1')
line2, = ax.plot([1, 2, 3], marker='o', label='Line 2')

ax.legend(handler_map={line1: HandlerLine2D(numpoints=4)})

在这里插入图片描述

如你所见,“第1行”现在有4个标记点,其中“第2行”有2个(默认值)。尝试上面的代码,只将map的键从第1行更改为type(第1行)。请注意,现在两个Line2D实例都有4个标记。

除了复杂给力类型(如误差图、词干图和直方图)的处理程序外,默认handler_map还有一个特殊的元组处理程序(legend_handler.HandlerTuple),它只是将给定元组中的每个项目的句柄绘制在彼此之上。以下示例演示了将两个图例键相互叠加的组合:

from numpy.random import randn

z = randn(10)

fig, ax = plt.subplots()
red_dot, = ax.plot(z, "ro", markersize=15)
# Put a white cross over some of the data.
white_cross, = ax.plot(z[:5], "w+", markeredgewidth=3, markersize=15)

ax.legend([red_dot, (red_dot, white_cross)], ["Attr A", "Attr A+B"])

在这里插入图片描述

legend_handler.HandlerTuple类还可用于将多个图例键分配给同一条目:

from matplotlib.legend_handler import HandlerLine2D, HandlerTuple

fig, ax = plt.subplots()
p1, = ax.plot([1, 2.5, 3], 'r-d')
p2, = ax.plot([3, 2, 1], 'k-o')

l = ax.legend([(p1, p2)], ['Two keys'], numpoints=1,
              handler_map={tuple: HandlerTuple(ndivide=None)})

在这里插入图片描述

实现自定义图例处理程序

可以实现自定义处理程序以将任何句柄转换为图例键(句柄不一定需要是matplotlib artist)。处理程序必须实现一个legend_artist方法,该方法返回单 个artist供图例使用。legend_artist所需的签名记录在legend_artist的文档中。

import matplotlib.patches as mpatches


class AnyObject:
    pass


class AnyObjectHandler:
    def legend_artist(self, legend, orig_handle, fontsize, handlebox):
        x0, y0 = handlebox.xdescent, handlebox.ydescent
        width, height = handlebox.width, handlebox.height
        patch = mpatches.Rectangle([x0, y0], width, height, facecolor='red',
                                   edgecolor='black', hatch='xx', lw=3,
                                   transform=handlebox.get_transform())
        handlebox.add_artist(patch)
        return patch

fig, ax = plt.subplots()

ax.legend([AnyObject()], ['My first handler'],
          handler_map={AnyObject: AnyObjectHandler()})

在这里插入图片描述

或者,如果我们想全局接受AnyObject实例,而不需要一直手动设置handler_map关键字,我们可以注册新的处理程序:

from matplotlib.legend import Legend
Legend.update_default_handler_map({AnyObject: AnyObjectHandler()})

虽然这里的力量是显而易见的,但请记住,已经实现了许多处理程序,并且你想要实现的目标可能已经可以通过现有类轻松实现。例如,要生成椭圆图例键,而不是矩形图例键:

from matplotlib.legend_handler import HandlerPatch


class HandlerEllipse(HandlerPatch):
    def create_artists(self, legend, orig_handle,
                       xdescent, ydescent, width, height, fontsize, trans):
        center = 0.5 * width - 0.5 * xdescent, 0.5 * height - 0.5 * ydescent
        p = mpatches.Ellipse(xy=center, width=width + xdescent,
                             height=height + ydescent)
        self.update_prop(p, orig_handle, legend)
        p.set_transform(trans)
        return [p]


c = mpatches.Circle((0.5, 0.5), 0.25, facecolor="green",
                    edgecolor="red", linewidth=3)

fig, ax = plt.subplots()

ax.add_patch(c)
ax.legend([c], ["An ellipse, not a rectangle"],
          handler_map={mpatches.Circle: HandlerEllipse()})

在这里插入图片描述

在这里插入图片描述

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

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

相关文章

【Image captioning】S2 Transformer for Image Captioning 实现流程

S2 Transformer for Image Captioning 实现流程 作者:安静到无声 个人主页 目录 S2 Transformer for Image Captioning 实现流程环境设置数据准备训练评价离线评估在线评估参考文献和引用参考引用致谢推荐专栏环境设置 克隆此存

代码随想录算法训练营第三十二天|122.买卖股票的最佳时机II 55. 跳跃游戏 45.跳跃游戏II

122.买卖股票的最佳时机II 本题解法很巧妙&#xff0c;大家可以看题思考一下&#xff0c;在看题解。 代码随想录 public int maxProfit(int[] prices) {int result 0;for (int i 1; i < prices.length; i) {result Math.max(prices[i] - prices[i - 1], 0);}return re…

【可定制、转换时间戳】解析nc文件,并保存为csv文件

解析nc文件&#xff0c;并保存为csv文件 写在最前面解析nc文件&#xff08;代码汇总放最后面&#xff09;读取nc文件获取气象文件中所有变量解析时间解析部分代码汇总 写入csv文件 写在最前面 愿称之为&#xff1a;支持私人订制、非常完美的版本 参考&#xff1a; 解析部分参…

C 风格文件输入/输出---无格式输入/输出

C 标准库的 C I/O 子集实现 C 风格流输入/输出操作。 <cstdio> 头文件提供通用文件支持并提供有窄和多字节字符输入/输出能力的函数&#xff0c;而 <cwchar>头文件提供有宽字符输入/输出能力的函数。 无格式输入/输出 从文件流获取字符 std::fgetc, std::getc …

TorchDynamo初探②:Torch.FX调研和实践

作者&#xff5c;strint 1 概要 torch.fx 是 PyTorch 官方发布的 Python 到 Python 的代码变换工具。如果你想做 Torch 代码变换&#xff0c;torch.fx 是首选工具。 torch.fx 会将 Torch 代码 trace 成 6 种基础的 node 组成的 graph&#xff0c;基于这个 graph 可以方便的做各…

01 PHP基础知识讲解

一 php基础知识 PHP文件的默认拓展名是“php”。 PHP文件中包含HTML标记、PHP标记、PHP代码以及空格和注释。 PHP标记&#xff1a;开始标记<?php 结束标记 ?> 中间内容是PHP代码。 PHP代码&#xff1a;学习第一个指令 echo 功能是用于输出字符串 。 语句结束符&a…

从零开始-与大语言模型对话学技术-gradio篇(4)

前言 本文介绍「星火杯」认知大模型场景创新赛中的落选项目- AI命理分析系统&#xff0c;属于个人娱乐练手。总结提炼了往期文章精华并发掘出新的知识。 包括本地部署版本和Web在线版本&#xff0c;两种打包方式基于 半自动化使用.bat手动打包迁移python项目 如何把 Gradio …

Minio集群搭建

一、官方文件 1、minio官网 https://min.io/ 2、中文文档 http://docs.minio.org.cn/docs/ 3、集群原理 二、集群部署 1、在每台服务器上创建minio目录 mkdir -p /app/minio/{run,data1,data2} && mkdir -p /etc/minio2、下载或者上传下载好的minio二进制文件 https…

net/http库中request.RemoteAddr的值不确定性-【Golang踩坑笔记】

环境信息&#xff1a; Go 1.20Windows 11 x64 代码示例 // 这里的r是框架传入的request&#xff0c;其中封装了net/http下的request.go中的Request fmt.Println("r.RemoteAddr:", r.RemoteAddr) // 本地执行时,该值可能是[::1]:port也可能是127.0.0.1:port 当在…

安装GPU驱动,CUDA Toolkit和配置与CUDA对应的Pytorch

如果有帮助,记得回来点个赞 目录 1.安装指定GPU驱动如果安装的GPU CUDA Version和CUDA Toolkit版本已经冲突怎么办? 2.安装指定版本的CUDA Toolkit如果我安装了CUDA Toolkit之后nvcc -V仍然显示旧的CUDA Toolkit版本怎么办? 3.安装与CUDA对应的Pytorch 1.安装指定GPU驱动 &…

C++之string

目录 1、了解string 2、string相关函数 3、相关函数的使用 ①构造函数 ②赋值 ③>>&#xff0c;<< ④operator[] ⑤size ⑥iterator(迭代器) ⑦push_back ⑧append ⑨ ⑩capacity ⑪reserve ⑫resize ⑬insert ⑭erase ⑮c_str ⑯find ⑰substr…

简化转换器:使用您理解的单词进行最先进的 NLP — 第 1 部分 — 输入

一、说明 变形金刚是一种深度学习架构&#xff0c;为人工智能的发展做出了杰出贡献。这是人工智能和整个技术领域的一个重要阶段&#xff0c;但也有点复杂。截至今天&#xff0c;变形金刚上有很多很好的资源&#xff0c;那么为什么要再制作一个呢&#xff1f;两个原因&#xff…

代码随想录第43天|416. 分割等和子集,1049. 最后一块石头的重量 II, ​494.目标和,​ 474.一和零(一窍不通)

416. 分割等和子集 思路 本题是01背包的应用题 背包的体积为sum / 2背包要放入的商品&#xff08;集合里的元素&#xff09;重量为 元素的数值&#xff0c;价值也为元素的数值背包如果正好装满&#xff0c;说明找到了总和为 sum / 2 的子集。背包中每一个元素是不可重复放入…

(其他) 剑指 Offer 67. 把字符串转换成整数 ——【Leetcode每日一题】

❓ 剑指 Offer 67. 把字符串转换成整数 难度&#xff1a;中等 写一个函数 StrToInt&#xff0c;实现把字符串转换成整数这个功能。不能使用 atoi 或者其他类似的库函数。 首先&#xff0c;该函数会根据需要丢弃无用的开头空格字符&#xff0c;直到寻找到第一个非空格的字符为…

C++学习笔记(堆栈、指针、命名空间、编译步骤)

C 1、堆和栈2、指针2.1、指针的本质2.2、指针的意义2.3、清空指针2.4、C类中的this 3、malloc and new4、命名空间4.1、创建命名空间4.2、使用命名空间 5、编译程序的四个步骤5.1、预处理5.2、编译5.3、汇编5.4、链接 1、堆和栈 堆&#xff08;heap&#xff09;和栈&#xff0…

领域驱动设计:DDD与微服务的关系

文章目录 基础概念软件架构模式的演进微服务设计和拆分的困境为什么 DDD 适合微服务&#xff1f;DDD 与微服务的关系 基础概念 DDD 虽然历史很久了&#xff0c;但它与微服务和中台设计的结合&#xff0c;却是一片很新的领域。早在 2003 年就诞生的 DDD&#xff0c;怎么来指导“…

基于spring boot+ vue开发的位置数据展现和分析平台源码 UWB源码

spring boot vue位置数据展现和分析平台源码 UWB室内外高精度定位系统源码 智慧工厂是现代工厂信息化发展的新阶段&#xff0c;基于UWB定位技术&#xff0c;融合位置物联网、GIS可视化等技术&#xff0c;实现对人员、物资精确管理。在重点区域设置电子围栏&#xff0c;无权限…

【Mysql】数据库第一讲(服务器数据库的安装和基础操作介绍)

数据库基础 &#x1f361;1.CentOs服务器数据库的安装&#x1f367;2.基础使用&#x1f368; 2.1 服务器&#xff0c;数据库&#xff0c;表关系&#x1f366;2.2使用案例&#xff1a; &#x1f967;3.数据库分类&#x1f9c1;4.存储引擎&#x1f370;4.Mysql库的操作&#x1f3…

YOLO目标检测——密集人群人头数据集+已标注yolo格式标签下载分享

实际项目应用&#xff1a;城市安防、交通管理、社会研究、商业应用、等多个领域数据集说明&#xff1a;YOLO密集人群人头目标检测数据集&#xff0c;真实场景的高质量图片数据&#xff0c;数据场景丰富&#xff0c;图片格式为jpg&#xff0c;共4300张图片。标注说明&#xff1a…

【web开发】6、Django(1)

提示&#xff1a;文章写完后&#xff0c;目录可以自动生成&#xff0c;如何生成可参考右边的帮助文档 文章目录 一、Django是什么&#xff1f;二、使用步骤1.安装Django2.创建项目3.创建app4.快速上手 数据库操作1.安装第三方模块2.自己创建数据库3.DJango链接数据库4.DJango操…