如何使Matplotlib绘图符合科研绘图规范

Matplotlib默认的绘图看起来太“轻佻”,这篇文章是关于如何让Matplotlib绘图看起来更加符合文献中图像的样子的。

画图全局参数设置

在科研绘图时,我们需要设置一些全局参数来保证图像的美观性和一致性。比如我们可以设置全局字体、字号、线宽、颜色等参数。全局参数使用plt.rcParams来设置。plt.rcParams是一个字典,包含了Matplotlib的所有可配置参数。我们可以通过修改这个字典来改变全局参数。

注意:全局参数必须在plt.plot()之前设置,否则不会生效。

以下是一些常用的全局参数设置:

1
2
3
4
5
6
7
8
9
10
import matplotlib.pyplot as plt
# 设置线宽
plt.rcParams["lines.linewidth"] = 1
plt.rcParams["font.family"] = "Times new roman"
plt.rcParams['font.serif'] = ['Times New Roman']
# 设置公式字体为times new roman
plt.rcParams['mathtext.fontset'] = 'stix' # 使用STIX字体,接近Times风格。这里不设置Times New Roman字体是因为Matplotlib不支持
# 刻度线朝内
plt.rcParams["xtick.direction"] = "in"
plt.rcParams["ytick.direction"] = "in"

设置图片大小及dpi

科研绘图,尤其是要用在论文中的图片,往往都有图片大小及dpi要求。图片大小就是图片的实际尺寸,matplotlib中的图片大小的默认单位是英寸(inch),dpi是每英寸的像素点数。

如何理解图片大小及dpi

  • 图片大小:图片的实际尺寸。例如图片大小为7 cm x 5 cm,那么这张图片放进word中时,不进行任何修改,查看到的大小就是7 cm x 5 cm。
  • dpi:每英寸的像素点数。
  • 图片像素大小:图片大小 * dpi。例如图片大小为7 cm x 5 cm,dpi为300,那么图片的像素大小就是7/2.54 * 300 x 5/2.54 * 300 = 826 x 591。
  • 图片大小和dpi的关系:在图片像素大小固定时,图片大小和dpi是成反比的。也就是说,图片大小越大,dpi越小;图片大小越小,dpi越大。我们可以通过设置图片大小和dpi来控制图片的清晰度和文件大小。

如何设置图片大小及dpi

我们可以使用figsize参数来设置图片大小,使用dpi参数来设置dpi。在科研绘图时,常用的图片大小单位是cm而非inch,因此可以通过定义转化函数进行转化。
请注意,dpi设置得越大,图片越清晰,但是绘图越慢。因此可以在绘图时设置较低的dpi,保存时设置较高的dpi。
注意

如果使用adjust_text库,可以在绘图时使用较高的dpi,这样可以提高自动调整文本位置的效果。
如果设置了图片渐变背景,请务必保证绘图dpi和保存dpi一致。

1
2
3
4
5
6
import matplotlib.pyplot as plt
def cm(x):
return x / 2.54

fig=plt.figure(figsize=(cm(7), cm(5)), dpi=1200)
fig.savefig("plot.png", dpi=1200)

设置坐标轴

我们希望在画图时,坐标轴的范围、刻度、标签等都能符合我们的要求。我们可以使用plt.xlim()plt.ylim()plt.xticks()plt.yticks()等函数来设置坐标轴。此外,在一般的科研绘图中,我们希望坐标轴每两个主刻度之间有一个次刻度。我们可以使用ax.yaxis.set_minor_locator(AutoMinorLocator(2))来设置次刻度的数量。AutoMinorLocator是一个自动生成次刻度的类,参数表示每两个主刻度之间有几个次刻度。我们还可以使用ax.xaxis.set_major_locator(MaxNLocator(5))来设置主刻度的数量。MaxNLocator是一个自动生成主刻度的类,参数表示最多有几个主刻度。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
import matplotlib.pyplot as plt
import numpy as np
from matplotlib.ticker import AutoMinorLocator, MaxNLocator
# 生成数据
x = np.linspace(0, 10, 100)
y = np.sin(x)
# 创建图形和坐标轴
fig, ax = plt.subplots()
# 绘制曲线
ax.plot(x, y)
# 设置坐标轴范围
xmin,xmax,xsep = 0, 10, 1
ymin,ymax,ysep = -1, 1, 0.2
plt.xlim(xmin, xmax)
plt.ylim(ymin, ymax)
# 设置x轴、y轴间距
plt.xticks(np.arange(xmin, xmax + xsep / 10, xsep))
plt.yticks(np.arange(ymin, ymax + ysep / 10, ysep))
# 设置坐标轴刻度
ax.xaxis.set_major_locator(MaxNLocator(5)) # 主刻度数量
ax.xaxis.set_minor_locator(AutoMinorLocator(2)) # 参数n=2表示主刻度之间分成2份(即1个小刻度)
ax.yaxis.set_major_locator(MaxNLocator(5)) # 主刻度数量
ax.yaxis.set_minor_locator(AutoMinorLocator(2)) # 参数n=2表示主刻度之间分成2份(即1个小刻度)
# 设置坐标轴标签
ax.set_xlabel("X-axis")
ax.set_ylabel("Y-axis")
# 设置坐标轴标题
ax.set_title("Title")

绘图结果

plot.png