【1】引言
前序学习中,已经发现坐标轴的显示具有至关重要的影响,因此今天继续探索相关技巧:坐标轴显隐设置。
前序学习内容可通过下述链接直达:
【2】官网教程
点击下方链接可以直达官网教程:
https://matplotlib.org/stable/gallery/spines/spines.html#sphx-glr-gallery-spines-spines-py
官网教程里面的关键词spines可以理解为坐标轴,而坐标轴上显示数字旁边凸出的小短线一般用tick来表示。
运行官网程序,获得的图像为图1,图1中圈出了部分spines上的tick:
图1
刚好以图1为基准,我们尝试辨析三个子图的不同:
【a】第一个图形的上下左右轴都显示;
【b】第二个图形只显示左轴和下轴;
【c】第三个图形只显示左轴和下轴,但是X轴只显示和自变量对应的区域,左轴和下轴不交叉。
为追溯这种不同的来源,我们需要读懂程序。
【3】代码解读
首先是引入画图和计算模块:
import matplotlib.pyplot as plt #引入画图模块 import numpy as np #引入计算模块
然后是完成变量定义:
x = np.linspace(0, 2 * np.pi, 100) #定义自变量 y = 2 * np.sin(x) #定义因变量
然后定义要画图:
fig, (ax0, ax1, ax2) = plt.subplots(nrows=3, layout='constrained') #定义要画图
然后先按照默认方式画第一个图,第一个图的坐标轴是完整的:
ax0.plot(x, y) #画第一个图形 ax0.set_title('normal spines') #命名第一个图形 ax1.plot(x, y) #画第二个图形 ax1.set_title('bottom-left spines') #命名第二个图形 # Hide the right and top spines ax1.spines.right.set_visible(False) #不显示第二个图形的右侧坐标轴 ax1.spines.top.set_visible(False) #不显示第二个图形的上侧坐标轴
但第二个图就约定了不显示右轴和上轴,通过spines.right.set_visible(False)和top.set_visible(False)实现:
ax1.spines.right.set_visible(False) #不显示第二个图形的右侧坐标轴 ax1.spines.top.set_visible(False) #不显示第二个图形的上侧坐标轴
然后输出第三个图形,第三个图形的轴输出范围通过 ax2.spines.bottom.set_bounds(x.min(), x.max()) 和ax2.spines.left.set_bounds(y.min(), y.max()) 进行控制:
ax2.plot(x, y) #命名第三个图形 ax2.set_title('spines with bounds limited to data range') #命名第三个图形 # Only draw spines for the data range, not in the margins ax2.spines.bottom.set_bounds(x.min(), x.max()) #设置第三个图形的下侧坐标轴,使其刚好和自变量对应 ax2.spines.left.set_bounds(y.min(), y.max()) #设置第三个图形的左侧坐标轴,使其刚好和因变量对应 # Hide the right and top spines ax2.spines.right.set_visible(False) #不显示第三个图形的右侧坐标轴 ax2.spines.top.set_visible(False) #不显示第三个图形的上侧坐标轴
最后输出图形:
plt.show() #输出图形
至此的完整代码为:
import matplotlib.pyplot as plt #引入画图模块
import numpy as np #引入计算模块
x = np.linspace(0, 2 * np.pi, 100) #定义自变量
y = 2 * np.sin(x) #定义因变量
# Constrained layout makes sure the labels don't overlap the Axes.
fig, (ax0, ax1, ax2) = plt.subplots(nrows=3, layout='constrained') #定义要画图
ax0.plot(x, y) #画第一个图形
ax0.set_title('normal spines') #命名第一个图形
ax1.plot(x, y) #画第二个图形
ax1.set_title('bottom-left spines') #命名第二个图形
# Hide the right and top spines
ax1.spines.right.set_visible(False) #不显示第二个图形的右侧坐标轴
ax1.spines.top.set_visible(False) #不显示第二个图形的上侧坐标轴
ax2.plot(x, y) #命名第三个图形
ax2.set_title('spines with bounds limited to data range') #命名第三个图形
# Only draw spines for the data range, not in the margins
ax2.spines.bottom.set_bounds(x.min(), x.max()) #设置第三个图形的下侧坐标轴,使其刚好和自变量对应
ax2.spines.left.set_bounds(y.min(), y.max()) #设置第三个图形的左侧坐标轴,使其刚好和因变量对应
# Hide the right and top spines
ax2.spines.right.set_visible(False) #不显示第三个图形的右侧坐标轴
ax2.spines.top.set_visible(False) #不显示第三个图形的上侧坐标轴
plt.show() #输出图形
【4】代码修改
在第二个图形中,只输出了左轴和右轴,现在尝试只输出右轴和上轴:
ax1.spines.right.set_visible(True) #不显示第二个图形的右侧坐标轴 ax1.spines.top.set_visible(True) #不显示第二个图形的上侧坐标轴 ax1.spines.left.set_visible(False) #不显示第二个图形的右侧坐标轴 ax1.spines.bottom.set_visible(False) #不显示第二个图形的上侧坐标轴
图2
由图2可见,第二个子图只显示了右侧和上侧坐标轴,但是轴标签依然保留在左侧和下侧,因此相关代码有必要跟随修改:
ax1.tick_params(top='on',bottom=[],left=[],right='on')
ax1.tick_params(labeltop='on',labelbottom=[],labelleft=[],labelright='off')
细心的读者会发现, labelright='off'一般的结果应该是不显示标签值,但实际运行结果却是显示,如图3。
图3
为此继续修改,将labelleft也设置一个值:
ax1.tick_params(top='on',bottom=[],left=[],right='on')
ax1.tick_params(labeltop='on',labelbottom=[],labelleft='dfgh',labelright='off')
运行程序获得的图像为:
图4
由图4可见:只要ax1.tick_params()函数中的子项如labelleft的值不是“[ ]”,那就回输出结果。
为此追溯官网:
其实这里没有细节描写,所以自己多做尝试显得尤为重要。
至此的完整代码为:
import matplotlib.pyplot as plt #引入画图模块
import numpy as np #引入计算模块
x = np.linspace(0, 2 * np.pi, 100) #定义自变量
y = 2 * np.sin(x) #定义因变量
# Constrained layout makes sure the labels don't overlap the Axes.
fig, (ax0, ax1, ax2) = plt.subplots(nrows=3, layout='constrained') #定义要画图
ax0.plot(x, y) #画第一个图形
ax0.set_title('normal spines') #命名第一个图形
ax1.plot(x, y) #画第二个图形
ax1.set_title('bottom-left spines') #命名第二个图形
# Hide the right and top spines
ax1.spines.right.set_visible(True) #不显示第二个图形的右侧坐标轴
ax1.spines.top.set_visible(True) #不显示第二个图形的上侧坐标轴
ax1.spines.left.set_visible(False) #不显示第二个图形的右侧坐标轴
ax1.spines.bottom.set_visible(False) #不显示第二个图形的上侧坐标轴
ax1.tick_params(top='on',bottom=[],left=[],right='on')
ax1.tick_params(labeltop='on',labelbottom=[],labelleft='dfgh',labelright='off')
ax2.plot(x, y) #命名第三个图形
ax2.set_title('spines with bounds limited to data range') #命名第三个图形
# Only draw spines for the data range, not in the margins
ax2.spines.bottom.set_bounds(x.min(), x.max()) #设置第三个图形的下侧坐标轴,使其刚好和自变量对应
ax2.spines.left.set_bounds(y.min(), y.max()) #设置第三个图形的左侧坐标轴,使其刚好和因变量对应
# Hide the right and top spines
ax2.spines.right.set_visible(False) #不显示第三个图形的右侧坐标轴
ax2.spines.top.set_visible(False) #不显示第三个图形的上侧坐标轴
plt.show() #输出图形
【5】代码完善
在前序学习中,已经基本掌握坐标轴共享的技巧,就以共享X轴为目标,参考下述文章:
设置代码:
fig, (ax0, ax1, ax2) = plt.subplots(nrows=3,layout='constrained', sharex=True) #定义要画图
获得的输出图形为:
图5
由图5可见,隐X轴共享,只在最底下显示X轴范围。
继续设置图形颜色和线型增加对比度:
图6
【6】总结
通过ax.spines.top/left/right/bottom.set_visible(True/False)()函数和ax.tick_params()函数实现坐标轴显隐设置。