问题描述
问题:
假设一个人想要在一个图形中放置4个子图-4行乘1列或1行乘4列。可以使用fig,axes = plt.subplots(nrows=...,ncols=...)
初始化此子图。但是,同时输入nrows=4,ncols=1
和输入nrows=1,ncols=4
会使axes
具有相同的axes.shape=(4,)
。由于这些形状相同,因此matplotlib如何确定图形的行数和列数? 可以从nrows
或ncols
的实例中获取fig
和axes
吗?
MWE:
如果以上内容不清楚,则可以运行以下代码来创建这样的子图(请注意print
语句):
import numpy as np
import matplotlib.pyplot as plt
## sample data
x = np.arange(10)
y1 = np.cos(x)
y2 = np.sin(x)
y3 = np.tan(x)
y4 = 1 / y3
## make easy to identify
labels = ('cos','sin','tan',r'$\frac{1}{tan}$')
facecolors = ('darkorange','steelblue','purple','green')
## initialize plot
# fig,axes = plt.subplots(nrows=2,ncols=2,figsize=(12,7)) ## shape=(2,2)
fig,axes = plt.subplots(nrows=4,ncols=1,7)) ## shape=(4,)
# fig,axes = plt.subplots(nrows=1,ncols=4,)
## verify shape of axes
print(axes.shape)
## create a plot
for ax,y,label,facecolor in zip(axes.ravel(),(y1,y2,y3,y4),labels,facecolors):
ax.plot(x,label=label,color=facecolor)
## add legend
fig.subplots_adjust(bottom=0.2)
fig.legend(loc='lower center',mode='expand',fontsize=8,ncol=4)
## fig.nrows outputs AttributeError: 'figure' object has no attribute 'nrows'.
## show and close
plt.show()
plt.close(fig)
different but related question的答案使用以下解决方案进行提及-但会输出错误:
for f in fig.get_children():
print(f.colNum,f.rowNum)
# AttributeError: 'Rectangle' object has no attribute 'colNum'
我想一个人可以迭代try-except
循环来做到这一点,但我想知道是否有一种更干净的方法。
解决方法
调用plt.subplots()
时,matplotlib使用GridSpec创建子图。除了用于创建初始轴的一种图形外,图形本身还可以具有多个GridSpec,因此您无法从图形本身获取GridSpec,但可以从坐标轴获取它:
fig,axes = plt.subplots(nrows=1,ncols=4) ## shape=(4,)
gs = axes[0].get_gridspec()
gs.nrows # return 1
gs.ncols # returns 4