Matplotlib 1.5 中的新特性(2015 年 10 月 29 日)#

注意

Matplotlib 1.5 支持 Python 2.7、3.4 和 3.5

交互式面向对象用法#

现在,所有 Artist 对象都会跟踪其内部状态是否已更改但尚未通过调用 draw 反映在显示中(“陈旧”状态)。因此,可以在交互式会话中实际确定给定的 Figure 是否需要重新绘制。

为了方便交互式使用,pyplot 中新增了 draw_all 方法,该方法将重新绘制所有“陈旧”的图形。

为了方便交互式使用,matplotlib 现在在 IPython 的 'post_execute' 事件或标准 Python REPL 中的显示钩子中注册了一个函数,以便在控制权返回到 REPL 之前自动调用 plt.draw_all。这确保了绘制命令被延迟并且只调用一次。

其结果是,对于交互式后端(包括 %matplotlib notebook)在交互模式下(使用 plt.ion()

import matplotlib.pyplot as plt
fig, ax = plt.subplots()
ln, = ax.plot([0, 1, 4, 9, 16])
plt.show()
ln.set_color('g')

将自动更新绘图为绿色。随后对 Artist 对象的任何修改也将如此。

这是 pyplot 内部结构更大范围整合和简化的第一步。

使用带标签数据(如 pandas DataFrames)#

接受数组作为输入的绘图方法现在也可以处理带标签的数据并解包这些数据。

这意味着以下两个示例生成相同的图

示例

df = pandas.DataFrame({"var1":[1,2,3,4,5,6], "var2":[1,2,3,4,5,6]})
plt.plot(df["var1"], df["var2"])

示例

plt.plot("var1", "var2", data=df)

这适用于大多数期望数组/序列作为输入的绘图方法。data 可以是任何支持 __getitem__dictpandas.DataFrameh5py 等)以通过字符串键访问类似 array 值的事物。

除此之外,还进行了一些其他更改,使得处理带标签的数据(例如 pandas.Series)变得更容易。

  • 对于带有 label 关键字参数的绘图方法,其中一个数据输入被指定为标签源。如果用户未提供 label,则将对该值对象进行自省以查找标签,目前是通过查找 name 属性。如果值对象没有 name 属性,但作为键在 data kwarg 中指定,则使用该键。在上述示例中,这两种情况都会产生一个隐式的 label="var2"

  • 如果未提供 x 参数,则 plot() 现在使用 Series 的索引而不是 np.arange(len(y))

在 rcParams 中添加了 axes.prop_cycle#

这是现在已弃用的 axes.color_cycle 参数的一种更通用的形式。现在,我们不仅可以循环颜色,还可以循环线型、填充图案以及几乎任何其他 artist 属性。循环器表示法用于定义属性循环。将循环器相加就像您将两个或更多属性循环 zip 到一起。

axes.prop_cycle: cycler('color', 'rgb') + cycler('lw', [1, 2, 3])

您甚至可以乘以循环器,这就像在两个或更多属性循环上使用 itertools.product

../../_images/sphx_glr_color_cycle_001.png

新颜色映射#

所有四个被提议作为新默认值的颜色映射都可用,分别为 'viridis'(2.0 中的新默认值)、'magma''plasma''inferno'

(源代码, 2x.png, png)

样式#

新增了多种样式,包括许多来自 Seaborn 项目的样式。此外,为了为即将到来的 2.0 样式更改版本做准备,还添加了 'classic' 和 'default' 样式。在此版本中,'default' 和 'classic' 样式是相同的。通过现在在您的脚本中使用它们,您可以帮助确保 matplotlib 未来升级时的平稳过渡,以便您可以在准备好时升级到华丽的新默认样式!

import matplotlib.style
matplotlib.style.use('classic')

'default' 样式将为您提供 matplotlib 最新绘图样式

matplotlib.style.use('default')

后端#

新的后端选择#

现在可以使用环境变量 MPLBACKEND 来设置 matplotlib 后端。

wx 后端已更新#

wx 后端现在可以与 wxPython classic 和 Phoenix 一起使用。

wxPython classic 必须至少是 2.8.12 版本,并且适用于 Python 2.x。截至 2015 年 5 月,wxPython Phoenix 尚无正式版本发布,但当前快照可在 Python 2.7+ 和 3.4+ 上运行。

如果您安装了多个版本的 wxPython,则用户代码负责设置 wxPython 版本。具体操作方法在示例 嵌入 wx #2 开头的注释中解释。

配置 (rcParams)#

添加了一些参数,另一些则得到了改进。

参数

描述

xaxis.labelpad, yaxis.labelpad

mplot3d 现在遵循这些属性,它们默认为 rcParams["axes.labelpad"](默认值:4.0

rcParams["axes.labelpad"](默认值:4.0

轴与标签之间的默认间距

rcParams["errorbar.capsize"](默认值:0.0

误差条末端帽的默认长度

rcParams["xtick.minor.visible"](默认值:False), rcParams["ytick.minor.visible"](默认值:False

次要 x/y 刻度的默认可见性

rcParams["legend.framealpha"](默认值:0.8

图例框的默认透明度

rcParams["legend.facecolor"](默认值:'inherit'

图例框的默认前景色(或从 rcParams["axes.facecolor"] 继承 'inherit'(默认值:'white'))

rcParams["legend.edgecolor"](默认值:'0.8'

图例框的默认边框颜色(或从 rcParams["axes.edgecolor"] 继承 'inherit'(默认值:'black'))

rcParams["figure.titlesize"](默认值:'large'

图形主标题的默认字体大小

rcParams["figure.titleweight"](默认值:'normal'

图形主标题的默认字体粗细

rcParams["image.composite_image"](默认值:True

保存时,矢量图形后端是否应将多个图像合成为单个图像。在 Inkscape 或其他程序中进一步编辑文件时很有用。

rcParams["markers.fillstyle"](默认值:'full'

标记的默认填充样式。可能的值有 'full'(默认)、'left''right''bottom''top''none'

rcParams["toolbar"](默认值:'toolbar2'

添加了 'toolmanager' 作为有效值,启用实验性的 ToolManager 功能。

小部件#

选择器的活动状态#

所有选择器现在都实现了 set_activeget_active 方法(在访问 active 属性时也会调用),以便正确更新和查询它们是否处于活动状态。

ignoreset_activeget_active 方法移动到基类 Widget#

将子类中的重复方法上移到父类以避免代码重复。

为 MultiCursor 添加启用/禁用功能#

MultiCursor 对象创建后可以禁用(和启用),而无需销毁该对象。示例

multi_cursor.active = False

改进了 RectangleSelector 并新增了 EllipseSelector 小部件#

添加了一个 *interactive* 关键字,该关键字允许在绘制形状后通过可见的句柄来操纵形状。

添加了键盘修改器,用于

  • 移动现有形状(默认键 = 'space')

  • 使形状呈正方形(默认 'shift')

  • 使初始点成为形状的中心(默认 'control')

  • 正方形和中心可以结合使用

允许 Artist 在光标中显示像素数据#

为 artist 添加了 get_cursor_dataformat_cursor_data 方法,可用于在状态栏的光标显示中添加 zdata。还为 Images 添加了实现。

新绘图功能#

文本自动换行#

为 Text 添加了关键字参数 "wrap",该参数在绘制时自动断开长文本行。适用于任何旋转的文本、不同的对齐模式以及作为标签或标题的文本。此换行发生在 Figure 边缘,而非 Axes 边缘。

(源代码, 2x.png, png)

等高线图角遮罩#

Ian Thomas 重写了计算等高线的 C++ 代码,以添加对角遮罩的支持。这由函数 contour()contourf() 中的新关键字参数 corner_mask 控制。之前的行为(现在通过使用 corner_mask=False 获得)是单个被遮罩点完全遮罩掉所有接触该点的四个四边形。新行为(通过使用 corner_mask=True 获得)仅遮罩接触该点的四边形的角;任何包含三个未遮罩点的三角形角照常绘制等高线。如果未指定 corner_mask 关键字参数,则默认值取自 rcParams。

../../_images/sphx_glr_contour_corner_mask_001.png

Line2D、Patch 和 Collection 的线型基本统一#

Line、Patch 和 Collection 的线型处理已统一。现在它们都支持使用短符号(如 "--")以及完整名称(如 "dashed")定义线型。此外,对于所有使用 Line2DPatchCollection 的方法,也支持使用虚线模式 ((0., [3., 3.])) 进行定义。

图例标记顺序#

新增了使用 markerfirst 关键字在图例框中将标签放置在标记之前的能力

支持 PolyCollection 和 stackplot 的图例#

PolyCollection 添加了 legend_handler,并为 stackplot() 添加了 labels 参数。

mplot3d 箭袋图支持备用枢轴点#

quiver 添加了一个 pivot kwarg,它控制箭袋线旋转的枢轴点。这还决定了箭头沿箭袋线的位置。

Logit 刻度#

新增对 'logit' 轴刻度的支持,这是一种非线性变换

\[x -> \log10(x / (1-x))\]

适用于 0 到 1 之间(不包括 0 和 1)的数据。

为 fill_between 添加 step kwargs#

Axes.fill_between 添加了 step kwarg,以允许填充使用 'step' 绘图样式绘制的线条之间的区域。step 的值与 Axes.stepwhere kwarg 的值匹配。关键字参数名称的不对称性并不理想,但 Axes.fill_between 已经有一个 where kwarg。

这对于绘制预分箱直方图特别有用。

方形图#

在轴函数中实现方形图功能作为新参数。当指定参数 'square' 时,会设置等比例缩放,并将限制设置为 xmax-xmin == ymax-ymin

(源代码, 2x.png, png)

更新了 figimage 以接受可选的 resize 参数#

新增了使用 plt.figimage(X, resize=True) 绘制简单二维数组的功能。这对于绘制没有轴或图像周围留白区域的简单二维数组很有用。

(源代码, 2x.png, png)

更新后的 Figure.savefig() 现在可以使用图形的 DPI#

新增了使用 dpi='figure' 以与屏幕上图形相同的 DPI 保存图形的功能。

示例

f = plt.figure(dpi=25)  # dpi set to 25
S = plt.scatter([1,2,3],[4,5,6])
f.savefig('output.png', dpi='figure')  # output savefig dpi set to 25 (same as figure)

更新了 Table 以控制边缘可见性#

新增了切换表格中线条可见性的功能。该功能已添加到 pyplot.table 工厂函数中,位于关键字参数 "edges" 下。值可以是字符串 "open"、"closed"、"horizontal"、"vertical" 或字母 "L"、"R"、"T"、"B" 的组合,分别代表左、右、上、下。

示例

table(..., edges="open")  # No line visible
table(..., edges="closed")  # All lines visible
table(..., edges="horizontal")  # Only top and bottom lines visible
table(..., edges="LT")  # Only left and top lines visible.

plot_wireframe 支持零 r/cstride#

Adam Hughes 为 mplot3d 的 plot_wireframe 添加了仅绘制行或列线图的支持。

(源代码, 2x.png, png)

绘制带标签的 bar 和 barh 图#

barbarh 添加了 kwarg *tick_label*,以支持绘制每个条形都带有文本标签的条形图。

(源代码, 2x.png, png)

为 pie 添加了 center 和 frame kwargs#

这些控制饼图的中心位置以及是否显示 Axes 框架。

修复了 3D 填充等高线图的多边形渲染问题#

某些情况下,生成具有多个孔洞的多边形的 3D 填充等高线图会由于 PolyCollectionPoly3DCollection 之间的路径信息丢失而导致渲染不正确。添加了函数 set_verts_and_codes(),以允许保留路径信息以进行正确渲染。

密集颜色条被栅格化#

矢量文件格式(pdf、ps、svg)对于许多类型的绘图元素而言效率很高,但对于某些元素,它们可能会导致文件大小过大,甚至产生渲染伪影,这取决于用于屏幕显示的渲染器。对于显示大量色调的颜色条来说,这是一个问题,这也是最常见的情况。现在,如果颜色条显示 50 种或更多颜色,它将在矢量后端中被栅格化。

DateFormatter strftime#

DateFormatter__call__ 方法将使用传递给格式化程序构造函数的格式字符串格式化 datetime.datetime 对象。此方法接受 1900 年之前的日期时间,这与 datetime.datetime.strftime() 不同。

文本的 Artist 级别 {get,set}_usetex#

Text 对象添加了 {get,set}_usetex 方法,该方法允许在 artist 级别控制 LaTeX 渲染与内部 mathtex 渲染。

Axes.remove() 按预期工作#

与添加到 Axes 的 artist 类似,Axes 对象可以通过 remove() 从其图形中移除。

Locators set_params() 函数中的 API 一致性修复#

set_params() 函数用于在 Locator 类型实例中设置参数,现在可供所有 Locator 类型使用。该实现还通过严格定义用户可以设置的参数来防止不安全的使用。

要使用它,请在 Locator 实例上调用 set_params() 并传入所需的参数

loc = matplotlib.ticker.LogLocator()
# Set given attributes for loc.
loc.set_params(numticks=8, numdecs=8, subs=[2.0], base=8)
# The below will error, as there is no such parameter for LogLocator
# named foo
# loc.set_params(foo='bar')

日期定位器#

日期定位器(派生自 DateLocator)现在实现了 tick_values 方法。这是所有派生自 Locator 的定位器所期望的。

现在可以轻松使用日期定位器而无需创建轴

from datetime import datetime
from matplotlib.dates import YearLocator
t0 = datetime(2002, 10, 9, 12, 10)
tf = datetime(2005, 10, 9, 12, 15)
loc = YearLocator()
values = loc.tick_values(t0, tf)

OffsetBox 现在支持裁剪#

Artist 通过 DrawingAreaTextAreaOffsetBox 类型的对象上绘制。 TextArea 计算文本所需的空间,因此文本始终在边界内,在这方面没有任何改变。

然而,DrawingArea 作为零个或多个在其上绘制且可能超出边界的 Artist 的父级。现在,子 Artist 可以被裁剪到 DrawingArea 的边界内。

tight_layout 现在考虑 OffsetBox#

当调用 tight_layout()Figure.tight_layoutGridSpec.tight_layout() 时,锚定在轴外部的 OffsetBox 不会被截断。在多个子图的情况下,OffsetBox 也不会被其他轴重叠。

多页 PDF(PdfPages)中的每页 PDF 备注#

为 PdfPages 类添加了一个新方法 attach_note(),允许将简单文本备注附加到多页图形 PDF 的页面中。新备注在具有此功能的查看器(Adobe Reader、OSX Preview、Skim 等)的 PDF 注释列表中可见。默认情况下,备注本身会保留在页面外,以防止其出现在打印件中。

必须在调用 savefig 之前调用 PdfPages.attach_note,以便将其添加到正确的图形中。

更新了 fignum_exists 以接受图形名称#

新增了使用图形名称而不是仅仅使用图形编号来检查图形是否存在的功能。示例

figure('figure')
fignum_exists('figure') #true

ToolManager#

Federico Ariza 编写了新的 ToolManager,它将替代 NavigationToolbar2

ToolManager 提供了一种新的方式来查看用户与图形的交互。之前我们有 NavigationToolbar2,它有自己的工具,如 zoom/pan/home/save/...,我们也有快捷键,如 yscale/grid/quit/....ToolManager 将所有这些操作重新定位为工具(位于 backend_tools),并定义了一种访问/触发/重新配置它们的方式。

工具栏已被 ToolContainerBase 取代,它们只是触发工具的 GUI 接口。但请放心,默认后端包含一个名为 toolbarToolContainerBase

注意

目前,我们发布此功能主要用于收集反馈,在另行通知之前应将其视为实验性功能,因为 API 可能会发生变化。目前,ToolManager 仅适用于 GTK3 和 Tk 后端。请确保使用其中一个。其余后端的移植即将推出。

要激活 ToolManager,请在文件顶部包含以下内容

>>> matplotlib.rcParams['toolbar'] = 'toolmanager'

与 ToolContainer 交互#

最重要的功能是能够轻松重新配置 ToolContainer(即工具栏)。例如,如果我们想删除“前进”按钮,只需这样做。

>>> fig.canvas.manager.toolmanager.remove_tool('forward')

现在,如果您想以编程方式触发“主页”按钮

>>> fig.canvas.manager.toolmanager.trigger_tool('home')

ToolManager 的新工具#

可以将新工具添加到 ToolManager

一个打印“You're awesome”的非常简单的工具将是

from matplotlib.backend_tools import ToolBase
class AwesomeTool(ToolBase):
    def trigger(self, *args, **kwargs):
        print("You're awesome")

要将此工具添加到 ToolManager

>>> fig.canvas.manager.toolmanager.add_tool('Awesome', AwesomeTool)

如果我们要为该工具添加快捷键(“d”)

>>> fig.canvas.manager.toolmanager.update_keymap('Awesome', 'd')

要将其添加到工具栏中的“foo”组中

>>> fig.canvas.manager.toolbar.add_tool('Awesome', 'foo')

还有第二类工具,即“可切换工具”,它们与我们的基本工具几乎相同,只是它们属于一个组,并且在该组内互斥。对于派生自 ToolToggleBase 的工具,有两个基本方法 enabledisable,它们在工具被切换时会自动调用。

完整示例位于 工具管理器

cbook.is_sequence_of_strings 识别字符串对象#

这主要是 pandas 存储字符串序列的方式

import pandas as pd
import matplotlib.cbook as cbook

a = np.array(['a', 'b', 'c'])
print(cbook.is_sequence_of_strings(a))  # True

a = np.array(['a', 'b', 'c'], dtype=object)
print(cbook.is_sequence_of_strings(a))  # True

s = pd.Series(['a', 'b', 'c'])
print(cbook.is_sequence_of_strings(s))  # True

此前,最后两次打印返回 false。

为 plot directive 添加了新的 close-figs 参数#

Matplotlib 有一个 sphinx 扩展 plot_directive,它用于在 sphinx 文档中创建图。Matplotlib 1.5 为 plot directive 添加了一个新选项 —— close-figs —— 它在创建图之前关闭任何先前的图形窗口。这有助于在使用 plot_directive 时避免一些令人惊讶的重复图。

支持 imread 的 URL 字符串参数#

现在,imread() 函数接受指向远程 PNG 文件的 URL 字符串。这避免了直接生成 HTTPResponse 对象。

IPython notebook 中动画的显示钩子#

Animation 实例新增了 _repr_html_ 方法,以支持在 notebook 中内联显示动画。用于显示的方法由 animation.html rc 参数控制,该参数目前支持 nonehtml5 值。none 是默认值,不执行任何显示。html5 将动画转换为 H.264 编码视频,并直接嵌入到 notebook 中。

不想使用 _repr_html_ 显示钩子的用户也可以手动调用 to_html5_video 方法来获取 HTML,并使用 IPython 的 HTML 显示类进行显示。

from IPython.display import HTML
HTML(anim.to_html5_video())

带前缀的 pkg-config 用于构建#

pkg-config 的处理已修复,现在可以使用环境变量 PKG_CONFIG 来设置它。如果您的工具链带前缀,这一点很重要。这与在构建之前设置 CCCXX 的方式类似。示例如下

export PKG_CONFIG=x86_64-pc-linux-gnu-pkg-config