matplotlib(四)核心模式以及注意事项

  matplotlib拥有广泛的代码库,对许多新用户来说可能令人生畏。但是,大多数matplotlib用法都可以通过一个相当简单的概念框架和一些重要知识来理解,所以,这篇博客主要介绍一些基本的使用模式、最佳实践以及注意事项,让你更深刻的认识matplotlib的工作方式。

matplotlib一般概念

提醒一句话:everything in matplotlib is organized in a hierarchy.

Parts of Image

这里写图片描述

state-machine environment

  在层次结构的最顶部是matplotlib “state-machine environment”,它由matplotlib.pyplot模块提供。在此级别,简单函数用于将绘图元素(线条,图像,文本等)添加到当前图形中的当前轴。Pyplot的 “state-machine environment”与MATLAB的行为类似,对于具有MATLAB经验的用户来说应该是最熟悉的 。

Figure

  即整个图像,该图记录了所有子轴,一些“特殊”的artist(标题,图形图例等)和画布(不要过于纠结画布,它是一个至关重要的,因为它是实际上绘图的对象,以获得你的Plot内容,但作为用户它或多或少是不可见的)。一个图像可以有任意数量的Axes,但是应该至少有一个。

fig = plt.figure()  # an empty figure with no axes
fig.suptitle('No axes on this figure')  # Add a title so we know which it is

fig, ax_lst = plt.subplots(2, 2)  # a figure with a 2x2 grid of Axes

这里写图片描述

Axes

  这就是所说的“plot”,它是具有数据空间的图像区域。给定的图形可以包含许多轴,但给定的Axes对象只能在一个图中。 Axes包含两个(或3D的三个)Axis对象(注意Axes和Axis之间的差异),它们负责数据限制(数据限制也可以通过set_xlim()set_ylim()来设置,每个Axes都有一个标题(通过set_title()设置),一个x标签(通过set_xlabel()设置)和一个通过set_ylabel()设置的y标签。

Axis

  这些是类似数字的对象,它们负责设置图形限制并生成刻度线和ticklabels(标记刻度线的字符串)。刻度线的位置由Locator对象确定,ticklabel字符串由Formatter格式化。正确的定位器和格式化器的组合可以非常精确地控制刻度位置和标签。

Artist

  基本上你在图上看到的一切都是artist,这包括Text对象,Line2D对象,集合对象,Patch对象……。渲染图形时,所有artist都被绘制到画布上。大多数artist都与轴有关;这样的artist不能被多个轴共享,也不能从一个轴移动到另一个轴。

matplotlib数据输入

  所有绘图函数都需要np.arraynp.ma.masked_array作为输入。像“array-like”的类(如pandas数据对象和np.matrix)可能会或可能不会按预期工作,最好在绘图之前将它们转换为np.array对象。

matplotlib、pyplot、pylab

  • matplotlib是整个包;
  • matplotlib.pyplot是matplotlib中的一个模块;
  • pylab是一个与matplotlib一起安装的模块;

  pylab是一个便利模块,它在单个名称空间中批量导入matplotlib.pyplot(用于绘图)和numpy(用于数学和使用数组)。虽然之前许多示例使用pylab,但不再推荐使用它。 另外,对于非交互式绘图,建议使用pyplot创建图形,然后使用OO界面进行绘图 。

Coding Style

编程风格很重要,对于matplotlib有两种编程风格,这在python matplotlib入门(一)Matplotlib工作流程 就总结过,一是 MATLAB-style,这是一种类似于matlab的代码风格;另一种是 OO-style,即面向对象的代码风格。

Backends

  matplotlib针对许多不同的用例和输出格式:有些人从python shell交互使用matplotlib,并在键入命令时弹出绘图窗口;有些人将matplotlib嵌入到图形用户界面(如wxpython或pygtk)中以构建丰富的应用程序;其他人在批处理脚本中使用matplotlib从一些数值模拟生成postscript图像;还有一些在Web应用程序服务器中生成posts动画以动态提供图形。 为了支持所有这些用例,matplotlib可以针对不同的输出,并且这些功能中的每一个都称为后端。“前端”是面向用户的代码,即绘图代码;而“后端”完成幕后的所有艰苦工作以制作图形。有两种类型的后端:用户界面后端和硬拷贝后端来制作图像文件(PNG,SVG,PDF,PS)。

# 方法1
#The backend parameter in your matplotlibrc file (see Customizing Matplotlib with style sheets and rcParams):

backend : WXAgg   # use wxpython with antigrain (agg) rendering

# 方法2
# If your script depends on a specific backend you can use the use() function:

import matplotlib
matplotlib.use('PS')   # generate postscript output by default

注意:如果使用use()函数,则必须在导入matplotlib.pyplot之前完成此操作。导入pyplot后调用use()将不起作用。如果用户想要使用不同的后端,则使用use()将需要更改代码。因此,除非绝对必要,否则应避免显式调用use()

Performance

  1. 使用快速样式

    快速样式可用于自动将简化和分块参数设置为合理的设置,以加快绘制大量数据的速度。它可以通过运行简单地使用:

    import matplotlib.style as mplstyle
    mplstyle.use('fast')
    
    
    # 也可以使用多个样式组合,并确保fast在最后
    
    mplstyle.use(['dark_background', 'ggplot', 'fast'])
  2. 线分块(chunk)

    
    # 仅适用于以agg作为后端时
    
    import numpy as np
    import matplotlib.pyplot as plt
    import matplotlib as mpl
    mpl.rcParams['path.simplify_threshold'] = 1.0
    
    
    # Setup, and create the data to plot
    
    y = np.random.rand(100000)
    y[50000:] *= 2
    y[np.logspace(1,np.log10(50000), 400).astype(int)] = -1
    
    mpl.rcParams['path.simplify'] = True
    
    mpl.rcParams['agg.path.chunksize'] = 0
    plt.plot(y)
    plt.show()
    
    mpl.rcParams['agg.path.chunksize'] = 10000
    plt.plot(y)
    plt.show()
  3. 标记简化

    标记也可以简化,尽管不如下面要介绍的线段简化强大 。标记简化仅适用于Line2D对象(通过属性markevery)。无论何处传递Line2D构造参数,例如matplotlib.pyplot.plot()matplotlib.axes.Axes.plot(),更多请参考 Markevery Demo

    plt.plot(x, y, markevery=10)

  4. 线段简化

    path.simplify参数是一个布尔值,表示线段是否简化;path.simplify_threshold参数控制简化的线段数量,更高的阈值会有更快的渲染。

    import numpy as np
    import matplotlib.pyplot as plt
    import matplotlib as mpl
    
    
    # Setup, and create the data to plot
    
    y = np.random.rand(100000)
    y[50000:] *= 2
    y[np.logspace(1, np.log10(50000), 400).astype(int)] = -1
    mpl.rcParams['path.simplify'] = True
    
    
    # simplify_threshold 默认是1/9
    
    mpl.rcParams['path.simplify_threshold'] = 0.0
    plt.plot(y)
    plt.show()
    
    mpl.rcParams['path.simplify_threshold'] = 1.0
    plt.plot(y)
    plt.show()
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章