Figure的add_subplot()方法
本篇讨论Figure对象的另一个重要方法: add_subplot()。
很多人会认为 add_subplot() 与 add_axes() 方法一样,都是向figure容器中添加axes子容器。
如果你也是这样理解add_subplot()方法的,你就真的有必要认真看看本篇了。
本篇将从4个方面来讨论:
add_subplot(self, *args, **kwargs)
add_subplot()方法,“向figure添加一个Axes作为一subplot布局的一部分。”
要调用add_subplot()方法,有4种签名形式:
add_subplot()方法本质上做了两件事:
我们就可以进一步在这个axes中绘制图形元素。
add_subplot()网格有两种定义方式:
第一种是用3个参数,分别代表网格的,行数 nrows, 列数 ncols, 索引号index。它们都是位置参数。这种是第1种调用签名形式。
第二种是用一个3位数的整数,如,224,第一个2表示2行,第二个2表示2列,第3位上的4表示第4个格子。这就是第二种调用签名形式,pos为224,也是位置参数。
如果我们不提供参数,即第4种调用签名,默认pos为111。
而第三种调用签名形式,请参考一篇中的相关内容。
假如,我们要创建一个2*2的网格,参数和索引如下图所示:
add_subplot()方法的网格参数和索引
下面的代码就在figure中创建了一个2*2的网格,并在第4个格子中创建了一个axes坐标系。
from matplotlib.backends.backend_agg import FigureCanvasAgg
from matplotlib.figure import Figure
from matplotlib.axes import Axes
import numpy as np
from numpy import math
fig =Figure(
dpi=100,
facecolor=(239/256,239/256,239/256),
edgecolor=(82/256,101/256,155/256),
linewidth=6.0,
frameon=True,
)
canvas = FigureCanvasAgg(fig)
#创建一个2*2的网格,并在第4个格子中创建一个axes
fig.add_subplot(224)
s, (width, height) = canvas.print_to_buffer()
from PIL import Image
im = Image.frombytes("RGBA", (width, height), s)
im.show()
注意:2*2的网格是虚拟的,起一个定位的作用,本例在第4个格子中创建axes。
再看下例:
from matplotlib.backends.backend_agg import FigureCanvasAgg
from matplotlib.figure import Figure
from matplotlib.axes import Axes
import numpy as np
from numpy import math
fig =Figure(
dpi=100,
facecolor=(239/256,239/256,239/256),
edgecolor=(82/256,101/256,155/256),
linewidth=6.0,
frameon=True,
)
canvas = FigureCanvasAgg(fig)
fig.add_subplot(224)
#再创建一个2行3列的虚拟网格
#在这个网格的第2个格子中创建axes
fig.add_subplot(232)
s, (width, height) = canvas.print_to_buffer()
from PIL import Image
im = Image.frombytes("RGBA", (width, height), s)
im.show()
使用add_subplot()实现复杂布局
上面代码,在同一个figure中使用不同的网格定义:
这样就实现了,不规则的、复杂的子图布局。
这才是add_subplot()方法最重要用途。
小结:
注意官方文档的表述差异:
两者创建的对象不同:
add_subplot()与add_axes()两者既紧密相关,也有区别:
add_subplot(self, *args, **kwargs)
向Figure添加一个子图subplot,add_suplot方法会自动创建一个Axes作为子图布置的一部分。
该方法是通过调用subplot_class_factory工厂函数创建子图和Axes的实例来实现上述功能的。
matplotlib有了一个axes子包,子包内有一个_subplots私有模块。_subpltos模块包含一个类和一个工厂函数:
class SubplotBase(object)用于subplots的基类,它们是:class: ’ Axes ‘实例,该实例带有其他方法,以方便生成和操作figure中的一组:class:’ Axes '。
工厂函数,首先,它是个函数,但工厂函数基本上都是带有返回对象的。而这些返回对象则是通过调用一种或者多种类来创建的对象。工厂函数:能够产生类实例的内建函数。
这将生成一个继承自SubplotBase和给定axes_class(假定axes_class是axes.axes的子类)的新类。像这样动态创建一个新类可能有点迂回,但这意味着不必为每种类型的坐标系创建一个新的Subplot类。
subplot_class_factory()工厂函数,继承了SubplotBase类和axes_calss参数给定的类,默认axes_class = Axes
查看该工厂函数的源码有助于理解它
def subplot_class_factory(axes_class=None):
if axes_class is None:
axes_class = Axes
try:
# Avoid creating two different instances of GeoAxesSubplot...
# Only a temporary backcompat fix. This should be removed in
# 3.4
return next(cls for cls in SubplotBase.__subclasses__()
if cls.__bases__ == (SubplotBase, axes_class))
except StopIteration:
return type("%sSubplot" % axes_class.__name__,
(SubplotBase, axes_class),
{'_axes_class': axes_class})
关注"Python草堂",完全掌握matplotlib。
(This end.)