精讲坐标轴系统(Axis)

精讲坐标轴系统(Axis)

续前文:

保姆级matplotlib教程:详细目录

保姆级seaborn教程:详细目录

seaborn和matplotlib怎么选,还是两个都要学?

详解Python matplotlib深度美化(第一期)

详解Python matplotlib深度美化(第二期)

详解matplotlib隐式pyplot法和显式axes法

Python matplotlib的上限:可“追星”,可“逐浪”!

Python“万水千山图”—山峦图/嵴线图/峰峦图

6.3.1 坐标轴系统简介

坐标系统主要有以下几种分类:

笛卡尔坐标系 (Cartesian Coordinate System):使用直角坐标轴,常见于平面图表。 极坐标系 (Polar Coordinate System):基于角度和半径,适用于表示旋转和周期性数据。 三维坐标系 (Three-Dimensional Coordinate System):在三维空间中使用三个坐标轴(X、Y、Z),用于展示三维数据。 地理坐标系 (Geographic Coordinate System):使用经纬度表示地理位置,常用于地图。 对数坐标系 (Logarithmic Coordinate System):Y轴或X轴使用对数尺度,适合表示变化幅度大的数据。

这些系统帮助以不同方式可视化和分析数据,主要通过projection参数设置,各自举个例子,

#6.3.1_01

# -*- encoding: utf-8 -*-

'''

未经过允许禁止转载!

@Author : 公众号:pythonic生物人

@Desc : 6.3.1 坐标轴系统简介

'''

import matplotlib.pyplot as plt

from mpl_toolkits.basemap import Basemap

import numpy as np

fig = plt.figure(figsize=(12, 10), dpi=150, frameon=True, edgecolor='grey')

fig.patch.set_linewidth(1)

# 笛卡尔坐标系

ax1 = fig.add_subplot(231) #默认使用笛卡尔坐标系,即直角坐标系

x = np.linspace(0, 10, 100)

y = np.sin(x)

ax1.plot(x, y)

ax1.set_title('笛卡尔坐标系')

ax1.set_xlabel('X轴')

ax1.set_ylabel('Y轴')

# 极坐标系

ax2 = fig.add_subplot(

232,

projection='polar' # 设置极坐标系

)

theta = np.linspace(0, 2 * np.pi, 100)

r = 1 + 0.5 * np.sin(5 * theta)

ax2.plot(theta, r)

ax2.set_title('极坐标系')

# 三维坐标系

ax3 = fig.add_subplot(

233,

projection='3d' #设置三维坐标系

)

x = np.random.rand(100)

y = np.random.rand(100)

z = np.random.rand(100)

ax3.scatter(x, y, z)

ax3.set_title('三维坐标系')

ax3.set_xlabel('X轴')

ax3.set_ylabel('Y轴')

ax3.set_zlabel('Z轴')

# 地理坐标系:绘制世界地图

ax4 = fig.add_subplot(234)

m = Basemap(

projection='ortho', #设置地图坐标系

lat_0=0,

lon_0=0,

ax=ax4)

m.drawcoastlines()

m.drawcountries()

m.drawmapboundary(fill_color='lightblue')

m.fillcontinents(color='lightgreen', lake_color='lightblue')

ax4.set_title('地理坐标系')

# 对数坐标系

ax5 = fig.add_subplot(235)

x = np.linspace(1, 10, 100)

y = np.log(x)

ax5.plot(x, y)

ax5.set_title('对数坐标系')

ax5.set_xlabel('X轴')

ax5.set_ylabel('log(Y轴)')

ax5.set_yscale('log') # 设置Y轴为对数尺度

ax6 = fig.add_subplot(236)

ax6.axis('off')

plt.tight_layout()

plt.show()

当前教程重点关注笛卡尔坐标系 (Cartesian Coordinate System),也就是直角坐标系统。

6.3.2 坐标轴边界(Spines)

在 Matplotlib 中,spines是围绕Axes边界的四条线(上下左右),它们定义了数据绘图区域的边框。Spines 可以用来设置图形的外框线,帮助强调不同的坐标轴。你可以根据需要自定义这些边框,比如隐藏某些边框、调整它们的位置、更改颜色和线宽等,例如,

#6.3.2_01

# -*- encoding: utf-8 -*-

'''

未经过允许禁止转载!

@Author : 公众号:pythonic生物人

@Desc : 6.3.2 坐标轴边界(Spines)

'''

import matplotlib.pyplot as plt

fig = plt.figure(figsize=(12, 10), dpi=150, frameon=True, edgecolor='grey')

fig.patch.set_linewidth(1)

axs = fig.subplots(2, 2)

# 第一个子图:什么是spines?

axs[0, 0].plot([1, 2, 3, 4], [1, 4, 9, 16])

axs[0, 0].set_title("什么是spines?")

axs[0, 0].annotate('左侧spine', xy=(1, 8), xytext=(1.5, 9),

arrowprops=dict(facecolor='black', shrink=0.05),

fontsize=10, color='black', ha='center', va='center')

axs[0, 0].annotate('右侧spine', xy=(4.1, 8), xytext=(3.5, 9),

arrowprops=dict(facecolor='black', shrink=0.05),

fontsize=10, color='black', ha='center', va='center')

axs[0, 0].annotate('顶部spine', xy=(2, 16), xytext=(2, 14),

arrowprops=dict(facecolor='black', shrink=0.05),

fontsize=10, color='black', ha='center', va='center')

axs[0, 0].annotate('底部spine', xy=(2, 0.5), xytext=(2, 2.5),

arrowprops=dict(facecolor='black', shrink=0.05),

fontsize=10, color='black', ha='center', va='center')

# 第二个子图:隐藏顶部和右侧的spines

axs[0, 1].plot([1, 2, 3, 4], [1, 4, 9, 16])

axs[0, 1].spines['top'].set_visible(False) #隐藏顶部的spines

axs[0, 1].spines['right'].set_visible(False) #隐藏右侧的spines

axs[0, 1].set_title("隐藏顶部和右侧的spines")

# 第三个子图:移动spines的位置

axs[1, 0].plot([-2, -1, 0, 1, 2], [-2, -1, 0, 1, 2])

axs[1, 0].spines['left'].set_position(('data', 0))

axs[1, 0].spines['bottom'].set_position(('data', 0))

axs[1, 0].set_title("移动spines的位置")

# 第四个子图:更改spines的颜色和线宽

axs[1, 1].plot([1, 2, 3, 4], [1, 4, 9, 16])

axs[1, 1].set_title("更改spines的颜色和线宽")

# 更改spines的颜色和线宽

axs[1, 1].spines['left'].set_color('red') #更改spines左侧的颜色

axs[1, 1].spines['left'].set_linewidth(2) #更改spines左侧的线宽

axs[1, 1].spines['bottom'].set_color('blue') #更改spines右侧的颜色

axs[1, 1].spines['bottom'].set_linewidth(2) #更改spines右侧的线宽

plt.tight_layout()

plt.show()

以上四个子图展示了spines常见的作用。

6.3.3 坐标轴比例(Axis Scales)

坐标轴比例(Axis Scales)的作用是控制数据在坐标轴上的展示方式。通过选择不同的比例,可以改变数据在图中的分布方式,从而更清晰地呈现出数据的特征。比如,使用线性比例会让数据均匀分布,而对数比例则适合处理跨度较大的数据,突出细节变化。不同的比例能帮助更好地分析和解释数据。

matplotlib主要支持以下各类坐标轴比例:

asinh(双曲正弦反函数比例),类似于对数比例,但能够处理正负数据,且对小数值更敏感。适用于范围较广的数据,尤其是正负值共存的情况。function(自定义函数比例),可以让用户自定义数据的缩放方式,通过提供前向和逆向函数来自定义映射。适合需要特殊转换的场景。functionlog(自定义对数比例),通过自定义的对数和逆对数函数来缩放数据,适用于需要灵活控制对数变换的情况,比如处理非常小的正数。linear(线性比例,默认),数据按照线性方式映射到坐标轴,适合数据值变化平稳、没有极端增长或减少的情况。log(对数比例),数据按对数方式缩放,适用于数据跨越多个数量级的场景,特别是指数增长的数据。logit(逻辑比例),常用于显示概率或分类数据,在 [0, 1] 区间内以逻辑函数缩放。适合处理百分比或概率数据的场景。symlog(对称对数比例),能够同时处理正值和负值的对数缩放,适合跨越正负区间的数据。

一个例子比较各类坐标轴比例的差异,

#6.3.3_01

# -*- encoding: utf-8 -*-

'''

未经过允许禁止转载!

@Author : 公众号:pythonic生物人

@Desc : 6.3.3 坐标轴比例(Axis Scales)

'''

titles = [

'asinh: 双曲正弦反函数比例', 'function: 自定义函数比例', 'functionlog: 自定义对数比例',

'linear: 线性比例', 'log: 对数比例', 'logit: 逻辑比例', 'symlog: 对称对数比例'

]

fig = plt.figure(figsize=(12, 10), dpi=150, frameon=True, edgecolor='grey')

fig.patch.set_linewidth(1)

axs = fig.subplots(2, 4)

axs = axs.flatten()

x = np.linspace(0, 10, 500)

y = np.arcsinh(x)

# Function Mercator transform

def forward(a):

a = np.deg2rad(a)

return np.rad2deg(np.log(np.abs(np.tan(a) + 1.0 / np.cos(a))))

def inverse(a):

a = np.deg2rad(a)

return np.rad2deg(np.arctan(np.sinh(a)))

# 依次应用标题及不同的坐标轴比例

for ax, title in zip(axs, titles):

ax.plot(x, y)

ax.set_title(title)

ax.grid(True)

if 'asinh' in title:

ax.set_yscale('asinh')

elif 'function: 自定义函数比例' in title:

ax.set_yscale('function', functions=(forward, inverse))

elif 'functionlog' in title:

ax.set_yscale('function', functions=(np.log1p, np.expm1))

else:

scale_type = title.split(':')[0]

ax.set_yscale(scale_type)

# 删除多余的子图

fig.delaxes(axs[-1])

plt.tight_layout()

plt.show()

注意观察以上Y轴的刻度变化,matplotlib主要通过set_yscale设置y轴的坐标轴比例,通过set_xscale设置x轴的坐标轴比例。

6.3.4 坐标轴刻度、刻度标签(Ticks、Tick labels)

每个坐标轴(Axis)上的 x 轴和 y 轴都有默认的刻度(Ticks)和刻度标签(Tick labels),刻度分为主刻度(major ticks)和次刻度(minor ticks),相应地,刻度标签也分为主刻度标签和次刻度标签。刻度用于标示坐标轴上的数据范围和间隔,而刻度标签则为这些刻度提供相应的文字或数值说明。

例如,上文章节“5.2.7 坐标轴刻度间隔、格式、大小、颜色等修改”的下图,以X轴为例子,主刻度、主刻度标签、副刻度、副刻度标签一目了然,

matplotlib可以通过set_xticks和set_yticks来设置刻度和刻度标签,也可以在坐标轴上高度自定义,本节详细介绍。

6.3.4.1 默认主坐标轴刻度、标签

Matplotlib默认的主坐标轴刻度和标签能满足绝大部分需求,一般无需设置,例如,

#6.3.4.1_01

# -*- encoding: utf-8 -*-

'''

未经过允许禁止转载!

@Author : 公众号:pythonic生物人

@Desc : 6.3.4.1 默认主坐标轴刻度、标签

'''

import matplotlib.pyplot as plt

import numpy as np

x1 = np.linspace(0, 10, 100)

y1 = np.sin(x1)

fig = plt.figure(figsize=(6, 3), dpi=100, frameon=True, edgecolor='grey')

fig.patch.set_linewidth(1)

ax1 = fig.add_subplot(111)

ax1.plot(x1, y1)

plt.show()

可以看到,matplotlib默认只显示主刻度,不显示副刻度。

6.3.4.2 自定义主坐标轴刻度、标签

可以使用 set_xticks 来自定义 x 轴的主刻度,使用 set_xticklabels 自定义 x 轴的主刻度标签;同样,使用 set_yticks 来自定义 y 轴的主刻度,而 set_yticklabels 则用于自定义 y 轴的主刻度标签。

例如,y轴刻度和标签只显示1和-1,x轴刻度和标签显示为pi,

#6.3.4.2_01

# -*- encoding: utf-8 -*-

'''

未经过允许禁止转载!

@Author : 公众号:pythonic生物人

@Desc : 6.3.4.2 自定义主坐标轴刻度、标签

'''

import matplotlib.pyplot as plt

import numpy as np

x1 = np.linspace(0, 3 * np.pi, 100)

y1 = np.sin(x1)

fig = plt.figure(figsize=(6, 3), dpi=100, frameon=True, edgecolor='grey')

fig.patch.set_linewidth(1)

ax1 = fig.add_subplot(111)

ax1.plot(x1, y1)

x_ticks = np.arange(np.pi / 2, 3.5 * np.pi, np.pi / 2)

x_labels = [

r'$\frac{\pi}{2}$', r'$\pi$', r'$\frac{3\pi}{2}$', r'$2\pi$',

r'$\frac{5\pi}{2}$', r'$3\pi$'

]

ax1.set_xticks(x_ticks) # 自定义x轴刻度

ax1.set_xticklabels(x_labels) # 自定义x轴刻度标签

ax1.set_yticks([-1, 1]) # 自定义y轴刻度

ax1.set_yticklabels(['-1', '1']) # 自定义y轴刻度标签

plt.show()

6.3.4.3 自定义副坐标轴刻度、标签

matplotlib默认情况下不显示副坐标轴的刻度和标签,但可以通过使用 set_xticks、set_xticklabels、set_yticks、set_yticklabels和tick_params来启用并自定义这些设置。

#6.3.4.3_01

# -*- encoding: utf-8 -*-

'''

未经过允许禁止转载!

@Author : 公众号:pythonic生物人

@Desc : 6.3.4.3 自定义副坐标轴刻度、标签

'''

import matplotlib.pyplot as plt

import numpy as np

x1 = np.linspace(0, 10, 100)

y1 = np.sin(x1)

fig = plt.figure(figsize=(6, 3), dpi=100, frameon=True, edgecolor='grey')

fig.patch.set_linewidth(1)

ax1 = fig.add_subplot(111)

ax1.plot(x1, y1)

# 设置副刻度

ax1.set_xticks(

np.arange(0, 10.5, 0.5), #自定义x轴副刻度

minor=True # 开启x轴副刻度

)

ax1.set_yticks(

np.arange(-1, 1.5, 0.25), #自定义y轴副刻度

minor=True # 开启y轴副刻度

)

# 设置副刻度标签

ax1.set_xticklabels([f'{i:.1f}' for i in np.arange(0, 10.5, 0.5)],

minor=True) # 自定义x轴副刻度标签格式

ax1.set_yticklabels([f'{i:.2f}' for i in np.arange(-1, 1.5, 0.25)],

minor=True) # 自定义y轴副刻度标签格式

# 调整副刻度样式

ax1.tick_params(which='minor', length=4, color='blue', labelsize=8)

plt.show()

进一步学习👉:

set_xticks

set_yticks

set_xticklabels

set_yticklabels

tick_params

6.3.4.4 自定义刻度、刻度标签外观

matplotlib中的tick_params方法可自定义诸如刻度的方向、长度、宽度、颜色、刻度标签的字体大小、旋转角度等属性。此外,还可以通过该函数控制主刻度和副刻度的显示及样式。

重点参数的含义如下:

axis:指定要影响的坐标轴,取值为 'x'、'y' 或 'both'。默认值为 'both'。which:指定作用的刻度类型,取值为 'major'(主刻度)、'minor'(副刻度)或 'both'。默认值为 'major'。direction:设置刻度的方向,取值为 'in'(朝内)、'out'(朝外)或 'inout'(两者)。默认值为 'out'。length:指定刻度线的长度,以点为单位。width:设置刻度线的宽度。color:定义刻度线的颜色。pad:设置刻度标签与刻度线之间的距离,以点为单位。labelsize:指定刻度标签的字体大小。labelcolor:定义刻度标签的颜色。grid_color:设置网格线的颜色。grid_alpha:控制网格线的透明度。grid_linewidth:指定网格线的宽度。grid_linestyle:定义网格线的线型,如 '-'(实线)、'--'(虚线)等。bottom/top/left/right:布尔值,用于控制是否显示各个边的刻度线。labelrotation:用于设置刻度标签的旋转角度。

重点介绍axis、which、direction、labelrotation参数。

重点参数1:axis

axis指定要影响的坐标轴,取值为 'x'、'y' 或 'both',默认值为 'both'。

举个例子介绍各个取值的效果,

#6.3.4.4_01

# -*- encoding: utf-8 -*-

'''

未经过允许禁止转载!

@Author : 公众号:pythonic生物人

@Desc : 6.3.4.4 自定义刻度、刻度标签外观

'''

import matplotlib.pyplot as plt

import numpy as np

# 创建数据

x = np.linspace(0, 10, 100)

y = np.sin(x)

fig, axs = plt.subplots(2,

2,

figsize=(10, 8),

dpi=150,

constrained_layout=True,

frameon=True,

edgecolor='grey')

fig.patch.set_linewidth(1)

# 第一个子图:默认刻度和标签

axs[0, 0].plot(x, y)

axs[0, 0].set_title('默认刻度和标签')

# 第二个子图:仅修改x轴的刻度和标签颜色

axs[0, 1].plot(x, y)

axs[0, 1].tick_params(

axis='x', #仅修改x轴的刻度和标签颜色

colors='red' #设置x轴的刻度和标签颜色为红色

)

axs[0, 1].set_title("仅修改x轴的刻度和标签颜色")

# 第三个子图:仅修改y轴的刻度和标签颜色

axs[1, 0].plot(x, y)

axs[1, 0].tick_params(

axis='y', #仅修改y轴的刻度和标签颜色

colors='red' #设置y轴的刻度和标签颜色为红色

)

axs[1, 0].set_title("仅修改y轴的刻度和标签颜色")

# 第四个子图:同时修改x轴和y轴的刻度和标签颜色

axs[1, 1].plot(x, y)

axs[1, 1].tick_params(

axis='both', #同时修改x轴和y轴的刻度和标签颜色

colors='red' #同时修改x轴和y轴的刻度和标签颜色为红色

)

axs[1, 1].set_title("同时修改x轴和y轴的刻度和标签颜色")

plt.show()

重点参数2:which

which指定作用的刻度类型,取值为 'major'(主刻度)、'minor'(副刻度)或 'both',默认值为 'major'。

举个例子,

#6.3.4.4_02

# -*- encoding: utf-8 -*-

'''

未经过允许禁止转载!

@Author : 公众号:pythonic生物人

@Desc : 6.3.4.4 自定义刻度、刻度标签外观

'''

import matplotlib.pyplot as plt

import numpy as np

# 创建数据

x = np.linspace(0, 10, 100)

y = np.sin(x)

# 创建图形和子图

fig, axs = plt.subplots(2, 2, figsize=(10, 8), dpi=150, edgecolor='grey')

fig.patch.set_linewidth(1)

# 第一个子图,使用默认值(仅主刻度)

axs[0, 0].plot(x, y)

axs[0, 0].set_title("默认 (which='major')")

axs[0, 0].tick_params(which='major', # 主刻度设置

length=8, width=2, color='red')

# 第二个子图,使用 'major' 作为 which 参数

axs[0, 1].plot(x, y)

axs[0, 1].set_title("which='major'")

axs[0, 1].tick_params(which='major',# 主刻度设置

length=8, width=2, color='red')

# 第三个子图,使用 'minor' 作为 which 参数

axs[1, 0].plot(x, y)

axs[1, 0].set_title("which='minor'")

axs[1, 0].tick_params(which='minor', # 副刻度设置

length=8, width=2, color='red')

#axs[1, 0].tick_params(which='major', length=8, width=2, color='red') # 主刻度设置

axs[1, 0].xaxis.set_minor_locator(plt.MultipleLocator(0.5))

axs[1, 0].yaxis.set_minor_locator(plt.MultipleLocator(0.25))

# 第四个子图,使用 'both' 作为 which 参数

axs[1, 1].plot(x, y)

axs[1, 1].set_title("which='both'")

axs[1, 1].tick_params(which='both',# 主刻度和副刻度设置

length=8, width=2, color='red')

axs[1, 1].xaxis.set_minor_locator(plt.MultipleLocator(0.5)) # 添加x轴副刻度

axs[1, 1].yaxis.set_minor_locator(plt.MultipleLocator(0.25)) # 添加y轴副刻度

# 调整布局

plt.tight_layout()

plt.show()

注意观察不同子图的变化。

重点参数3:direction

direction设置刻度的方向,取值为 'in'(朝内)、'out'(朝外)或 'inout'(两者),默认值为 'out'。

#6.3.4.4_03

# -*- encoding: utf-8 -*-

'''

未经过允许禁止转载!

@Author : 公众号:pythonic生物人

@Desc : 6.3.4.4 自定义刻度、刻度标签外观

'''

import matplotlib.pyplot as plt

import numpy as np

# 创建数据

x = np.linspace(0, 10, 100)

y = np.sin(x)

fig, axs = plt.subplots(2, 2, figsize=(10, 8), dpi=150, edgecolor='grey')

fig.patch.set_linewidth(1)

# 默认设置(direction=default)

axs[0, 0].plot(x, y)

axs[0, 0].set_title("默认 (direction='out')")

axs[0, 0].tick_params(length=8, width=2, color='red')

# 设置为 'in'(朝内)

axs[0, 1].plot(x, y)

axs[0, 1].set_title("direction='in'")

axs[0, 1].tick_params(

direction='in', #朝内

length=8,

width=2,

color='red')

# 设置为 'out'(朝外)

axs[1, 0].plot(x, y)

axs[1, 0].set_title("direction='out'")

axs[1, 0].tick_params(

direction='out', #朝外

length=8,

width=2,

color='red')

# 设置为 'inout'(两者)

axs[1, 1].plot(x, y)

axs[1, 1].set_title("direction='inout'")

axs[1, 1].tick_params(

direction='inout', #朝内外

length=8,

width=2,

color='red')

plt.tight_layout()

plt.show()

重点参数4:labelrotation

labelrotation用于设置刻度标签的旋转角度。

#6.3.4.4_04

# -*- encoding: utf-8 -*-

'''

未经过允许禁止转载!

@Author : 公众号:pythonic生物人

@Desc : 6.3.4.4 自定义刻度、刻度标签外观

'''

import matplotlib.pyplot as plt

import numpy as np

# 创建数据

x = np.linspace(0, 10, 10)

y = np.sin(x)

# 创建图形和子图

fig, axs = plt.subplots(2, 2, figsize=(10, 8), dpi=150, edgecolor='grey')

fig.patch.set_linewidth(1)

# 默认设置(labelrotation=0)

axs[0, 0].plot(x, y)

axs[0, 0].set_title("默认 (labelrotation=0)")

axs[0, 0].set_xticks(x)

axs[0, 0].set_xticklabels(

[f'{i:.1f}' for i in x],

rotation=0 # 默认设置为0度

)

# 设置为 45度

axs[0, 1].plot(x, y)

axs[0, 1].set_title("labelrotation=45°")

axs[0, 1].set_xticks(x)

axs[0, 1].set_xticklabels(

[f'{i:.1f}' for i in x],

rotation=45 # 设置为45度旋转

)

# 设置为 90度

axs[1, 0].plot(x, y)

axs[1, 0].set_title("labelrotation=90°")

axs[1, 0].set_xticks(x)

axs[1, 0].set_xticklabels(

[f'{i:.1f}' for i in x],

rotation=90 # 设置为90度旋转

)

# 设置为 120度

axs[1, 1].plot(x, y)

axs[1, 1].set_title("labelrotation=120°")

axs[1, 1].set_xticks(x)

axs[1, 1].set_xticklabels(

[f'{i:.1f}' for i in x],

rotation=120 # 设置为120度旋转

)

plt.tight_layout()

plt.show()

其它参数

#6.3.4.4_05

# -*- encoding: utf-8 -*-

'''

未经过允许禁止转载!

@Author : 公众号:pythonic生物人

@Desc : 6.3.4.4 自定义刻度、刻度标签外观

'''

import matplotlib.pyplot as plt

import numpy as np

# 创建数据

x = np.linspace(0, 10, 100)

y = np.sin(x)

fig, axs = plt.subplots(2, 2, figsize=(10, 8), dpi=100, edgecolor='grey')

fig.patch.set_linewidth(1)

# 1. 子图1: 设置刻度长度'length'

axs[0, 0].plot(x, y)

axs[0, 0].set_title("length=10")

axs[0, 0].tick_params(length=10 # 刻度线长度为10

)

# 2. 子图2: 设置刻度宽度'width'

axs[0, 1].plot(x, y)

axs[0, 1].set_title("width=2")

axs[0, 1].tick_params(width=2 # 刻度线宽度为2

)

# 3. 子图3: 设置刻度颜色'color'

axs[1, 0].plot(x, y)

axs[1, 0].set_title("color='red'")

axs[1, 0].tick_params(color='red' # 刻度线颜色为红色

)

# 4. 子图4: 设置刻度标签大小'labelsize'

axs[1, 1].plot(x, y)

axs[1, 1].set_title("labelsize=15")

axs[1, 1].tick_params(labelsize=15 # 刻度标签大小为15

)

plt.tight_layout()

plt.show()

更多参数不一一举例了。

6.3.4.5 自动定义刻度

上文6.3.4.2~6.3.4.4章节介绍了手动设置刻度的方法,能够满足大多数使用场景。然而,在实时数据可视化、交互式图表或数据范围不确定的情况下,自动调整刻度可以根据数据范围和视图动态更新,确保图表始终清晰易读,减少了手动调整的需求。

matplotlib使用坐标轴刻度定位器(locator)自动定义刻度,即自动为刻度安排恰当的位置。这些方法都在ticker中,

#6.3.4.5_01

# -*- encoding: utf-8 -*-

'''

未经过允许禁止转载!

@Author : 公众号:pythonic生物人

@Desc : 6.3.4.5 自动定义刻度

'''

import matplotlib.ticker as ticker

# 获取可用的Tick Locators

tick_locators = [

loc for loc in dir(ticker) if 'Locator' in loc and loc != 'Locator'

]

# 输出Tick Locators

print("可用的刻度定位器:")

for loc in tick_locators:

print(loc, end=',')

可用的刻度定位器:

AsinhLocator,AutoLocator,AutoMinorLocator,FixedLocator,IndexLocator,LinearLocator,LogLocator,LogitLocator,MaxNLocator,MultipleLocator,NullLocator,SymmetricalLogLocator,

每种定位器简介

Locator 名称定义和作用MaxNLocator该定位器根据用户指定的最大刻度数量,智能地选择刻度位置,适合需要简洁展示的图表。AutoLocator自动调整刻度位置以适应数据范围,确保主刻度均匀分布,是处理各种数据时的可靠选择。AutoMinorLocator这个定位器会自动添加次刻度,为图表提供更多细节,使得数据展示更加清晰。LinearLocator按照设定的刻度数量,在特定范围内均匀分布刻度,非常适合需要精确定量分析的数据。LogLocator在对数刻度上设置刻度,能够很好地处理指数增长或衰减的数据,确保刻度在对数尺度上合理分布。MultipleLocator通过设置固定间隔的刻度,这个定位器适合展示定期数据,如时间序列分析,帮助用户更好地理解趋势。FixedLocator允许用户根据特定位置设置刻度,适用于那些需要精准刻度的特殊情况,让图表更加直观。IndexLocator根据数据点的索引设置刻度,非常适合展示离散数据,帮助用户快速定位到特定的数值。NullLocator隐藏所有刻度,这个定位器在某些情况下尤其有用,比如只需展示图像而非具体数值的场合。SymmetricalLogLocator在对称对数刻度上设置刻度,非常适合处理数据分布中正负值对称的情况,增强视觉效果,使数据展示更具美感。AsinhLocator用于设置双曲正弦刻度,尤其适合处理范围广泛但对称的数据。LogitLocator在 logit 刻度上设置刻度,适合展示比例数据,确保刻度在 [0, 1] 范围内均匀分布。

每一种举一个简单的例子,

#6.3.4.5_02

# -*- encoding: utf-8 -*-

'''

未经过允许禁止转载!

@Author : 公众号:pythonic生物人

@Desc : 6.3.4.5 自动定义刻度

'''

import matplotlib.pyplot as plt

import numpy as np

import matplotlib.ticker as ticker

# 生成示例数据

x = np.linspace(-10, 10, 100)

y = np.sinh(x)

fig, axs = plt.subplots(6, 2, figsize=(14, 30), dpi=150, edgecolor='grey')

fig.patch.set_linewidth(1)

axs = axs.flatten()

# 子图 1:MaxNLocator

ax1 = axs[0]

ax1.plot(x, y, label="sinh(x)")

ax1.set_title("MaxNLocator (n=2)")

ax1.xaxis.set_major_locator(ticker.MaxNLocator(nbins=2) #限制x轴的刻度数量为2

)

ax1.grid(True, linestyle='--', alpha=0.7)

ax1.legend()

for tick in ax1.xaxis.get_major_ticks():

tick.label1.set_color("red")

# 子图 2:AutoLocator

ax2 = axs[1]

ax2.plot(x, y, label="sinh(x)")

ax2.set_title("AutoLocator")

ax2.yaxis.set_major_locator(ticker.AutoLocator() #自动设置主刻度

)

ax2.grid(True, linestyle='--', alpha=0.7)

ax2.legend()

for tick in ax2.yaxis.get_major_ticks():

tick.label1.set_color("red")

# 子图 3:AutoMinorLocator

ax3 = axs[2]

ax3.plot(x, y, label="sinh(x)")

ax3.set_title("AutoMinorLocator")

ax3.yaxis.set_minor_locator(ticker.AutoMinorLocator() #自动设置次刻度

)

ax3.grid(True, which='both', linestyle='--', alpha=0.7)

ax3.legend()

ax3.tick_params(axis='y', which='minor', color='red', width=2, size=8)

# 子图 4:LinearLocator

ax4 = axs[3]

ax4.plot(x, y, label="sinh(x)")

ax4.set_title("LinearLocator (numticks=6)")

ax4.xaxis.set_major_locator(ticker.LinearLocator(numticks=6) #设置6个均匀分布的刻度

)

ax4.grid(True, linestyle='--', alpha=0.7)

ax4.legend()

for tick in ax4.xaxis.get_major_ticks():

tick.label1.set_color("red")

# 子图 5:LogLocator

ax5 = axs[4]

ax5.plot(x, y, label="sinh(x)")

ax5.set_title("LogLocator")

ax5.set_xscale("log") # 设置x轴为对数刻度

ax5.xaxis.set_major_locator(ticker.LogLocator(

base=10.0, #使用10为底的对数刻度

))

ax5.grid(True, which='both', linestyle='--', alpha=0.7)

ax5.legend()

for tick in ax5.xaxis.get_major_ticks():

tick.label1.set_color("red")

# 子图 6:MultipleLocator

ax6 = axs[5]

ax6.plot(x, y, label="sinh(x)")

ax6.set_title("MultipleLocator (interval=2)")

ax6.xaxis.set_major_locator(ticker.MultipleLocator(2) # 设置固定间隔为2的刻度

)

ax6.grid(True, linestyle='--', alpha=0.7)

ax6.legend()

for tick in ax6.xaxis.get_major_ticks():

tick.label1.set_color("red")

# 子图 7:FixedLocator

ax7 = axs[6]

ax7.plot(x, y, label="sinh(x)")

ax7.set_title("FixedLocator (positions=[-5, 0, 5])")

ax7.xaxis.set_major_locator(ticker.FixedLocator([-5, 0, 5]) #设置具体的刻度位置

)

ax7.grid(True, linestyle='--', alpha=0.7)

ax7.legend()

for tick in ax7.xaxis.get_major_ticks():

tick.label1.set_color("red")

# 子图 8:IndexLocator

ax8 = axs[7]

ax8.plot(x, y, label="sinh(x)")

ax8.set_title("IndexLocator (base=3, offset=-6)")

ax8.xaxis.set_major_locator(ticker.IndexLocator(

base=3, #间隔

offset=-6 #起始刻度

)) #根据索引位置设置刻度

ax8.grid(True, linestyle='--', alpha=0.7)

ax8.legend()

for tick in ax8.xaxis.get_major_ticks():

tick.label1.set_color("red")

# 子图 9:NullLocator

ax9 = axs[8]

ax9.plot(x, y, label="sinh(x)")

ax9.set_title("NullLocator (No ticks)")

ax9.xaxis.set_major_locator(ticker.NullLocator() #隐藏所有刻度

)

ax9.grid(True, linestyle='--', alpha=0.7)

ax9.legend()

# 子图 10:SymmetricalLogLocator

x_sym = np.linspace(-10, 10, 100)

y_sym = np.sinh(x_sym)

ax10 = axs[9]

ax10.plot(x_sym, y_sym, label="sinh(x)")

ax10.set_title("SymmetricalLogLocator (linthresh=1)")

ax10.set_yscale("symlog", linthresh=1) # 设定linthresh=1以对称刻度

ax10.yaxis.set_major_locator(

ticker.SymmetricalLogLocator(

base=10, #对数基数为10

linthresh=1 #在-1到1之间使用线性刻度,而不使用对数刻度。

)) #在对称对数坐标轴上设置刻度

ax10.grid(True, which='both', linestyle='--', alpha=0.7)

ax10.legend()

for tick in ax10.yaxis.get_major_ticks():

tick.label1.set_color("red")

# 子图 11:AsinhLocator

ax11 = axs[10]

x_asinh = np.linspace(0, 10, 100)

y_asinh = np.sinh(x_asinh)

ax11.plot(x_asinh, y_asinh, label="sinh(x)")

ax11.set_title("AsinhLocator (linear_width=1.0)")

ax11.yaxis.set_major_locator(

ticker.AsinhLocator(linear_width=1.0)) #自动确定在asinh缩放轴上刻度线的最佳位置

ax11.grid(True, which='both', linestyle='--', alpha=0.7)

ax11.legend()

for tick in ax11.yaxis.get_major_ticks():

tick.label1.set_color("red")

# 子图 12:LogitLocator

ax12 = axs[11]

x_logit = np.linspace(0.01, 0.99, 100)

y_logit = x_logit

ax12.plot(x_logit, y_logit, label="y=x")

ax12.set_title("LogitLocator")

ax12.set_yscale("logit")

ax12.yaxis.set_major_locator(ticker.LogitLocator()) #在 logit 刻度上设置刻度,适合展示比例数据

ax12.grid(True, which='both', linestyle='--', alpha=0.7)

ax12.legend()

for tick in ax12.yaxis.get_major_ticks():

tick.label1.set_color("red")

plt.tight_layout()

plt.show()

红色为坐标轴刻度定位器的效果。

6.3.4.6 自动定义刻度标签格式

上文6.3.4.2~6.3.4.4章节介绍了手动设置刻度标签的方法,能够满足大多数使用场景。这里介绍matplotlib内置的另外一些定义刻度标签格式的方法。

matplotlib使用格式生成器(formatter)定义刻度标签格式,定义了与轴上刻度相关联的数值如何格式化为字符串。

#6.3.4.6_01

# -*- encoding: utf-8 -*-

'''

未经过允许禁止转载!

@Author : 公众号:pythonic生物人

@Desc : 6.3.4.6 自动定义刻度标签格式

'''

import matplotlib.ticker as ticker

# 获取可用的Tick Formatters

tick_formatters = [

loc for loc in dir(ticker) if 'Formatter' in loc and loc != 'Formatter'

]

# 输出Tick Locators

print("可用的刻度标签格式生成器:")

for loc in tick_formatters:

print(loc, end=',')

可用的刻度标签格式生成器: EngFormatter,FixedFormatter,FormatStrFormatter,FuncFormatter,LogFormatter,LogFormatterExponent,LogFormatterMathtext,LogFormatterSciNotation,LogitFormatter,NullFormatter,PercentFormatter,ScalarFormatter,StrMethodFormatter。

刻度标签格式生成器的作用如下表,

Formatter 名称定义和作用EngFormatter这个格式化器以工程格式显示数值,使得大的数值更易于阅读。它会使用每三位数的前缀,比如 k(千)、M(百万)、G(十亿),非常适合处理大数值的场景。FixedFormatter如果你需要在刻度上显示特定的标签而不是默认的数值,FixedFormatter 就是你的理想选择。它允许你手动设置每个刻度的标签,非常适合需要自定义标签的情况。FormatStrFormatter这个格式化器让你可以使用格式字符串(类似于 Python 的 % 格式化)来控制刻度标签的输出样式。无论是想显示小数位数还是特定格式,这个工具都能满足你的需求。FuncFormatterFuncFormatter 的强大之处在于你可以通过自定义函数来格式化刻度标签。这样,无论你的需求多独特,你都可以实现自己想要的输出格式,给予你极大的灵活性。LogFormatter当你在使用对数坐标轴时,LogFormatter 可以帮助你更好地格式化刻度标签。它支持自定义对数基数和其他格式设置,让你的数据展示更清晰。LogFormatterExponent如果你需要以指数形式显示刻度标签,LogFormatterExponent 就是一个不错的选择。它特别适合处理数值很大的情况,可以让读者迅速理解数据的规模。LogFormatterMathtext想在刻度标签中展示数学公式吗?LogFormatterMathtext 就可以帮你实现。它使用 Mathtext 格式,适合那些希望以更专业方式展示数据的用户。LogFormatterSciNotation处理非常大的或非常小的数值时,LogFormatterSciNotation 可以将刻度标签格式化为科学记数法,帮助读者更容易理解数值的范围。LogitFormatter如果你的数据是概率值(介于 0 和 1 之间),LogitFormatter 会将这些数值转换为 logit 格式进行显示,适合处理概率统计数据。NullFormatter当你希望完全隐藏刻度标签时,NullFormatter 是一个很好的选择。它能让图表看起来更加简洁,适合不需要刻度标签的情境。PercentFormatterPercentFormatter 能将刻度标签格式化为百分比,并且可以设置小数位数,特别适合展示比例数据,让读者一目了然。ScalarFormatter这是 Matplotlib 的默认标量格式化器,它会根据数值的大小智能选择显示方式,无论是普通数字还是科学记数法,能够确保你的数据展示清晰。StrMethodFormatter使用 StrMethodFormatter 让你可以运用 Python 的字符串格式化方法(如 str.format())来定义刻度标签的样式。这样可以实现更复杂的格式,提升数据展示的灵活性。

每一种formatter使用举例,

#6.3.4.6_02

# -*- encoding: utf-8 -*-

'''

未经过允许禁止转载!

@Author : 公众号:pythonic生物人

@Desc : 6.3.4.6 自动定义刻度标签格式

'''

import matplotlib.pyplot as plt

import numpy as np

import matplotlib.ticker as ticker

# 生成示例数据

x = np.linspace(0, 1e7, 100)

y = np.sin(x / 1e6)

#fig, axs = plt.subplots(6, 2, dpi=150, figsize=(14, 20))

fig, axs = plt.subplots(6, 2, figsize=(14, 30), dpi=150, edgecolor='grey')

fig.patch.set_linewidth(1)

axs = axs.flatten()

# Formatter 1: EngFormatter

ax1 = axs[0]

ax1.plot(x, y)

ax1.set_title("EngFormatter")

ax1.set_xlabel("Value (engineering prefixes)")

ax1.set_ylabel("Sin value")

ax1.xaxis.set_major_formatter(

ticker.EngFormatter(unit='MHz' #指定刻度标签单位。例如,振动次数设置为MHz,替代1e7

))

for tick in ax1.xaxis.get_major_ticks():

tick.label1.set_color("red")

# Formatter 2: FixedFormatter

ax2 = axs[1]

ax2.plot(x, y)

ax2.set_title("FixedFormatter")

ax2.set_yticks([0, 0.5, 1.0])

ax2.yaxis.set_major_formatter(

ticker.FixedFormatter(["0 km", "0.5 km", "1.0 km"] #传入刻度标签列表

))

for tick in ax2.yaxis.get_major_ticks():

tick.label1.set_color("red")

# Formatter 3: FormatStrFormatter

ax3 = axs[2]

ax3.plot(x, y)

ax3.set_title("FormatStrFormatter")

ax3.set_xticks([2000000, 6000000, 10000000])

ax3.xaxis.set_major_formatter(

ticker.FormatStrFormatter('Label: %d' #格式化刻度标签,使用常见python字符串格式化输出方法

))

for tick in ax3.xaxis.get_major_ticks():

tick.label1.set_color("red")

# Formatter 4: FuncFormatter

ax4 = axs[3]

ax4.plot(x, y)

ax4.set_title("FuncFormatter")

ax4.xaxis.set_major_formatter(

ticker.FuncFormatter(

lambda val, pos: f'{val:.1f} m' #轻松调用任何函数格式化标签,这里使用lambda函数

))

for tick in ax4.xaxis.get_major_ticks():

tick.label1.set_color("red")

# Formatter 5: LogFormatter

ax5 = axs[4]

x_log = np.linspace(1, 1000, 100)

y_log = np.log10(x_log)

ax5.plot(x_log, y_log)

ax5.set_title("LogFormatter")

ax5.xaxis.set_major_formatter(ticker.LogFormatter() #显示10^3中的10^3

)

for tick in ax5.xaxis.get_major_ticks():

tick.label1.set_color("red")

# Formatter 6: LogFormatterExponent

ax6 = axs[5]

ax6.plot(x_log, y_log)

ax6.set_title("LogFormatterExponent")

ax6.xaxis.set_major_formatter(ticker.LogFormatterExponent() #显示10^3中的3,对比子图5学习

)

for tick in ax6.xaxis.get_major_ticks():

tick.label1.set_color("red")

# Formatter 7: LogFormatterMathtext

ax7 = axs[6]

ax7.plot(x_log, y_log)

ax7.set_title("LogFormatterMathtext")

ax7.xaxis.set_major_formatter(ticker.LogFormatterMathtext() #科学计数法

)

for tick in ax7.xaxis.get_major_ticks():

tick.label1.set_color("red")

# Formatter 8: LogFormatterSciNotation

ax8 = axs[7]

ax8.plot(x_log, y_log)

ax8.set_title("LogFormatterSciNotation")

ax8.xaxis.set_major_formatter(ticker.LogFormatterSciNotation() #与前一种方法类似

)

for tick in ax8.xaxis.get_major_ticks():

tick.label1.set_color("red")

# Formatter 9: LogitFormatter

ax9 = axs[8]

x_logit = np.linspace(0.01, 0.99, 100)

y_logit = x_logit

ax9.plot(x_logit, y_logit)

ax9.set_title("LogitFormatter")

ax9.set_yscale("logit")

ax9.yaxis.set_major_formatter(ticker.LogitFormatter() #Probability格式

)

for tick in ax9.yaxis.get_major_ticks():

tick.label1.set_color("red")

# Formatter 10: NullFormatter

ax10 = axs[9]

ax10.plot(x, y)

ax10.set_title("NullFormatter")

ax10.xaxis.set_major_formatter(ticker.NullFormatter() #隐藏刻度标签

)

# Formatter 11: PercentFormatter

ax11 = axs[10]

percent_data = np.linspace(0, 1, 100)

ax11.plot(percent_data, percent_data)

ax11.set_title("PercentFormatter")

ax11.xaxis.set_major_formatter(ticker.PercentFormatter(xmax=1) #刻度标签使用百分数

)

for tick in ax11.xaxis.get_major_ticks():

tick.label1.set_color("red")

# Formatter 12: ScalarFormatter

ax12 = axs[11]

ax12.plot(x, y)

ax12.set_title("ScalarFormatter")

ax12.xaxis.set_major_formatter(ticker.ScalarFormatter() #默认方法

)

for tick in ax12.xaxis.get_major_ticks():

tick.label1.set_color("red")

plt.tight_layout()

plt.show()

红色为坐标轴刻度标签格式生成器的效果。

详解Python matplotlib坐标轴

相关推荐

iPhone 手机如何快速拨打电话?
网彩365平台下载

iPhone 手机如何快速拨打电话?

📅 07-29 👁️ 3756