《用Python进行科学计算》——matplotlib

什么是matplotlib?

patplotlib是python最著名的绘图库,提供了一整套与matlab相似的命令API,十分适合交互地进行制图。而且也可以方便地将它作为绘图控件,嵌入GUI应用中。
Gallery页面中有很多缩略图,打开之后都有源程序。如果你需要绘制某种类型的图,只需在这个页面中复制粘贴就基本可以搞定。

快速绘图

matplotlib的pyplot子库提供了和matlab类似的绘图API,方便用户绘制2D图表。

#coding:utf-8

import numpy as np
import matplotlib.pyplot as plt


x=np.linspace(0,10,1000)
y=np.sin(x)
z=np.cos(x**2)


plt.figure(figsize=(8,4))

#通过调用plot函数在当前的绘图对象中进行绘图
#用法:第一句将x,y数组传递给plot之后,用关键字指定各种属性。
	#label:给所绘制的曲线一个名字,此名字在图示legend中显示,只要在字符前后添加“$”符号,matplotlib就会使用其内嵌的latex引擎绘制的数学公式。
	#color:指定曲线颜色
	#linewidth:指定曲线的宽度
plt.plot(x,y,label="$sin(x)$",color="red",linewidth=2)
plt.plot(x,z,"b--",label="$cos(x^2)$")

#设置x轴的文字
plt.xlabel("Time(s)")

#设置Y轴的文字
plt.ylabel("Volt")

#设置图表的标题
plt.title("PyPlot First Example")

#设置Y轴的范围
plt.ylim(-1.2,1.2)

#显示图示
plt.legend()

#显示出创建的所有绘图对象
plt.show()

在这里插入图片描述
pylab模块
matplotlib提供了名为pylab的模块,其中包括了许多numpy和pyplot中常用的函数,方便用户快速进行计算和绘图,可以用于Ipython中的快速交互使用。

plt.figure(figsize=(8,4))

调用figure创建一个绘图对象,并且是它成为当前的绘图对象。
也可以不创建绘图对象直接调用plot,matplotlib会自动创建一个绘图对象。如果需要同时绘制多幅图表的话,可以是给figure传达一个整数参数指定图表的序号,如果所指定的序号的汇入对象已经存在的话,将不创建新的对象,而只是让它成为当前绘图对象。
通过figsize参数可以指定绘图对象的宽度和高度,单位为英寸;
dpi参数指定绘图对象的分辨率,即每英寸多少个像素,缺省值为80.

配置属性
matplotlib所绘制的图的每个组成部分都应有一个对象。我们可以通过调用这些对象的属性设置方法set_*或者pyplot的属性设置函数setp设置其属性值。

In [2]: import numpy as np

In [3]: import matplotlib.pyplot as plt

In [4]: x=np.arange(0,5,0.1)

In [5]: line, =plt.plot(x,x*x) #plot返回一个列表,通过line获取其第一个元素

In [6]: #调用Line2D对象的set_*方法设置属性值

In [7]: line.set_antialiased(False)

In [8]: #同时绘制sin和cos两条曲线,lines是一个有两个Line2D对象的列表

In [9]: lines=plt.plot(x,np.sin(x),np.cos(x))

In [10]: #调用setp函数同时配置多个Line2D对象的多个属性值

In [11]: plt.setp(lines,color="r",linewidth=2.0)
Out[11]: [None, None, None, None]

通过调用Line2D对象line的set_antialiased方法,关闭对象的反锯齿效果。或者通过调用plt.setp函数配置多个Line2D对性的颜色和线宽属性。

使用get_*方法或取对象的属性。

In [12]: line.get_linewidth()
Out[12]: 1.5

In [13]: plt.getp(lines[0],"color") #返回color属性
Out[13]: 'r'

In [14]: plt.getp(lines[1]) #返回所有属性
    agg_filter = None
    alpha = None
    animated = False
    antialiased = True
...

getp方法只能对一个对象进行操作,它有两种用法:

  • 指定属性名:返沪对象的指定属性的值
  • 不指定属性名:打印出对象的所有属性和它们的值

matplotlib的整个图表为一个Figrue对象,此对象在调用plt.figrue函数时返回,我们可以通过plt.gcf函数获取当前的绘图对象。

In [16]: f=plt.gcf()

In [17]: plt.getp(f)
    agg_filter = None
    alpha = None
    animated = False
    axes = [<matplotlib.axes._subplots.AxesSubplot object at ...
 ... ...

Figure对象中有一个axes属性,其值为AxesSubplot对象的列表,每个AxesSubplot对象代表图表中的一个子图,前面所绘制的图表只包含一个子图,当前子图可以通过plt.gca获得:

In [18]: plt.getp(f,"axes")
Out[18]: [<matplotlib.axes._subplots.AxesSubplot at 0x7efd25e73208>]
In [20]: plt.gca()
Out[20]: <matplotlib.axes._subplots.AxesSubplot at 0x7efd25e73208>

用plt.getp可以发现AxesSubplot对象有很多属性,例如它的lines属性为此子图所包含的Line2D对象列表:

In [21]: alllines=plt.getp(plt.gca(),"lines")

In [22]: alllines
Out[22]: <a list of 3 Line2D objects>

In [23]: alllines[0]==line
Out[23]: True

In [24]: #其中第一条曲线就是最开始绘制的那条

绘制多轴图

一个绘图对象可以包含多个轴,在Matplotlib中用轴表示一个绘图区域,可以将其理解为子图。可以使用subplot函数快速绘制有多个轴的图表。subplot函数的调用形式如下:

subplot(numRows, numCols, plotNum)

subplot将整个绘图区域等分为numRows行*numCols列个子区域,然后按照从左到右,从上到下的顺序对每个子区域进行编号,左上的编号为1.如果numRows,numCols和plotNum这三个数都小于10的话,可以把它们缩写为一个整数。如subplot(323)和subplot(3,2,3)是相同的。subplot在plotNum指定的区域中创建一个轴对象。如果新创建的轴和之前创建的轴和之前创建的轴重叠的话,之前的轴将被删除。

plt.subplot(321) #第一行第一个
plt.subplot(323) #第二行第一个
plt.subplot(313) #第三行一整行

在这里插入图片描述
当绘图对象有多个轴的时候,可以通过工具栏中的Configure Subplots按钮,交互地调节轴之间的间距距离。如果希望在程序中调节的话,可以调用subplots_adjust函数,它有left, right, bottom, top, wspace, hspace等几个关键字参数,这些参数的值都是0到1之间的小数,它们是以绘图区域的宽高为1进行正规化之后的坐标或者长度。

配置文件
一幅图有许多需要配置的属性,例如颜色,字体,线型等。我们在绘图时并没有对这些属性进行配置,许多都直接采用Matplotlib的缺省配置。Matplotlib将缺省配置保存在一个文件中,通过该这个文件,我们可以修改这些属性值。
使用配置文件matplotlinrc时的搜索路径

  • 当前路径:程序的当前路径
  • 用户配置路径:通常为HOME/.matplitlib/可以通过改变MATPLOTLIBRC修改
  • 系统配置路径:保存在matplotlib的安装目录下的mpl-data下。

获取用户配置路径:

import matplotlib

print(matplotlib.get_configdir())

获取目前使用的配置文件路径:

print(matplotlib.matplotlib_fname())
# /home/kiosk/.local/lib/python3.6/site-packages/matplotlib/mpl-data/matplotlibrc

系统配置路径下的配置文件,

import os
print(os.getcwd())
# /home/kiosk/Desktop/Project/Data

如果将matplotlibrc复制一份到脚本的当前目录下:

print(matplotlib.matplotlib_fname())
# /home/kiosk/Desktop/Project/Data/matplotlibrc

如果你用文本编辑器打开配置文件,你会发现它实际上是定义了一个字典。为了对众多的配置进行区分,关键字可以用点分开。
配置文件的读入可以使用rc_params函数,他返回一个配置字典:

print(matplotlib.rc_params())

"""
animation.avconv_path: avconv
animation.bitrate: -1
animation.codec: h264
animation.convert_args: []
animation.convert_path: convert
animation.embed_limit: 20.0
......
"""

在matplotlib模块载入的时候会调用rc_params,并把得到的配置字典保存到rcParams变量中:

In [26]: matplotlib.rcParams
Out[26]: 
RcParams({'_internal.classic_mode': False,
          'agg.path.chunksize': 0,
          'animation.avconv_args': [],
          'animation.avconv_path': 'avconv',
          'animation.bitrate': -1,
          'animation.codec': 'h264',
......

matplotlib将使用rcParams中的配置进行绘图。用户可以直接修改此字典中的配置,所做的改变会但应到此后所绘制的图中。
例如下面的脚本中所绘制的线将带有圆形的点标识符:
注意在此设置的配置不会真正的写入配置文件中。

matplotlib.rcParams["lines.marker"]="o"
import pylab
pylab.plot([1,2,3])
pylab.show()

在这里插入图片描述
为了方便配置,可以先使用rc函数,下面的例子同时配置点标识符、线宽和颜色:

matplotlib.rc("lines", marker="x", linewidth=2, color="red")

如果希望恢复到缺省配置(matplotlib载入时从配置文件读入的配置)的话,可以调用rcdefaluts函数。

matplotlib.rcParams["lines.marker"]="o"
import pylab
pylab.plot([1,2,3,4,5,6])

matplotlib.rcdefaults()
pylab.plot([-1,-2,-3])

pylab.show()

在这里插入图片描述
如果手工修改了配置文件,希望从配置文件重新载入最新的配置的话,可以调用:

matplotlib.rcParams.update( matplotlib.rc_params() )

Artist对象

matplotlib API包含有三层:

  • backend_bases.FigureCanvas:图表的绘制区域;
  • backend_bases.Renderer:知道如何在FigureCanvas上如何绘图;
  • artist.Artist:知道如何使用Renderer在FigureCanvas上绘图;

FigureCanvas和Render需要处理底层的绘图操作,Artist则处理所有的高层结构,例如处理图表、文字和曲线等的绘制和布局。通常我们只和Artist打交道,则不需要关心底层的绘制细节。

Artists分为简单类型和容器类型两种:
简单类型的Artists为标准的绘图元件例如Line2D、Rectangle、Text等

容器类型则可以包含许多简单类型的Artists,使它们组织一个整体,例如Axis、Axes、Figure等。
注意: Figure相当于一个桌面,Axes相当于上面的画纸

直接使用Artists创建图表的标准流程如下:

  • 创建Figure对象
  • 用Figure对象创建一个或者多个Axes和Subplot对象;
  • 调用Aexis等对象的方法创建各种简单类型的Artists;
#coding:utf-8

import matplotlib.pyplot as plt


# 1.调用pyplot.figure辅助函数创建figure对象
fig=plt.figure()

# 2.调用Figure对象的add_axes方法在其中创建一个Axes对象
#add_axes的参数是一个形如[left,bottom,width,height]的列表
# 这些数值分别指定所创建的Axes对象相对于fig的位置和大小,取值都在0~1之间
ax=fig.add_axes([0.15,0.1,0.7,0.3])

# 3.调用ax的plot方法绘图,创建一条曲线,并且返回此曲线对象(Line2D)
line, =ax.plot([1,2,3],[1,2,1])

print(ax.lines)

# [<matplotlib.lines.Line2D object at 0x7f811f036e10>]

print(line)

# Line2D(_line0)

# ax.lines是一个为包含ax的所有曲线的列表,后续的ax.plot调用会往此列表中
# 添加心的曲线。如果想删除某条曲线,直接从此列表中删除即可

Axes对象还包括许多其他的Artists对象
例如我们可以通过调用set_xlabel设置其x轴上的标题;

ax.set_xlabel("time")

如果查看set_xlabel的源代码,会发现它是通过调用下面的语句实现的:

self.xaxis.set_label_text(xlabel, fontdict, **kwargs)

如果一直跟踪下去会发现Axes的xaxis属性是一个XAxis对象;

self.xaxis = maxis.XAxis(self)
...
class XAxis(Axis):
...
print(ax.xaxis)
# XAxis(96.000000,48.000000)
#<matplotlib.axis.XAxis object at 0x06343230>

XAxis的label属性是一个Text对象

print(ax.xaxis.label)
# Text(0.5, 0, 'time')
#<matplotlib.text.Text object at 0x06343290>

而Text对象的_text属性为我们设置的值:

print(ax.xaxis.label._text)
# time

这些对象都是Artists,因此也可以调用它们的属性获取函数来获得相应的属性:

print(ax.xaxis.label.get_text())
# time

Artist的属性
图表中的每个元素都用一个matplotlib的Artists对象表示,而每个Artist对象都有一大堆属性控制其显示效果。例如Figure对象和Aexs对象都有patch属性作为其背景,他是一个Rectangle对象。通过它的一些属性可以修改figure图表的背景颜色或者透明度等属性。

fig=plt.figure()
fig.patch.set_color("g")
fig.canvas.draw()

patch的color属性通过set_color函数进行设置,属性修改之后并不会立即反映到图表上,还需调用fig.canvas.draw()才能显示。
下面是Artists对象的一些属性:

属性描述
alpha透明度,值在0到1之间,0为完全透明,1为完全不透明
animated布尔值,在绘制动画效果中使用
axes此Artist对象所在的Axes对象,可能为None
clip_box对象的裁剪框
clip_on是否裁剪
clip_path裁剪的路径
contains判断指定点是否在对象上的函数
figure所在的Figure对象可能为None
label文本标签
picker控制Artist对象的选取
transform控制偏移旋转
visible是否可见
zorder控制绘图顺序

Artist对象的所有属性都通过相应的get_*和set_*函数进行读写,例如下面的语句将alpha(透明度)属性设置为当前值的一半:
缺省的alpha属性值为None

fig.patch.set_alpha(0.5*fig.patch.get_alpha())

如果你想用一条语句设置多个属性的话,可以使用set函数:

fig.patch.set(alpha=0.7,zorder=2)

使用前面介绍的matplotlib.pyplot.getp函数可以方便地输出Artist对象的所有属性名和值:

print(plt.getp(fig.patch))

"""
agg_filter = None
    alpha = None
    animated = False
    antialiased = False
    bbox = Bbox(x0=0.0, y0=0.0, x1=1.0, y1=1.0)
    capstyle = butt
    children = []
    clip_box = None
    clip_on = True
    clip_path = None
    contains = None
    ...
"""

Figure容器
最大的Artist容器是matplotlib.figure.figure,它包括组成的所有元素。图表背景是一个Rectangle对象,用Figrue.patch属性表示。当你通过调用add_subplot或者add_axes方法往图表中添加轴(子图)时,这些子图都将添加到Figure.axes属性中,同时这两个方法也返回添加进axes属性的对象,注意返回值的类型有所不同,实际上AxesSubplot是Axes的子类。

import matplotlib.pyplot as plt

fig=plt.figure()

ax1=fig.add_subplot(211)
ax2=fig.add_axes([0.1,0.1,0.7,0.3])
plt.show()

print(ax1)
# AxesSubplot(0.125,0.53;0.775x0.35)

print(ax2)
# Axes(0.1,0.1;0.7x0.3)

print(fig.axes)
# [<matplotlib.axes._subplots.AxesSubplot object at 0x7f28c9917fd0>,
#  <matplotlib.axes._axes.Axes object at 0x7f28c29b0e80>]

为了支持pyplot中的gca()等函数,Figure对象内部保存有当前轴的信息,因此不建议直接对Figure.axes属性进行列表操作,而因该使用add_subplot, add_axes, delaxes等方法进行添加和删除操作。但是使用for循环对axes中的每个元素继续操作是没有问题的,下面的语句打开所有子图的栅格:

import matplotlib.pyplot as plt

fig=plt.figure()

ax1=fig.add_subplot(211)
ax2=fig.add_axes([0.1,0.1,0.7,0.3])

for ax in fig.axes:
    ax.grid(True)

plt.show()

在这里插入图片描述
Figure对象可以拥有自己的文字、线条以及图像等简单类型的Artist。缺省的坐标系统为像素点,但是可以通过设置Artsist对象的transform属性修改坐标系的转换方式。最常用的Figure对象的坐标系是以左下角为坐标原点(0,0),右上角为坐标(1,1)。下面的程序创建并添加两条直线到fig中:

#coding:utf-8

from matplotlib.lines import Line2D
import matplotlib.pyplot as plt

fig=plt.figure()
line1=Line2D([0,1],[0,1],transform=fig.transFigure,figure=fig,color="r")
line2=Line2D([0,1],[1,0],transform=fig.transFigure,figure=fig,color="g")

fig.lines.extend([line1,line2])
plt.show()

在这里插入图片描述

**注意:**为了让所创建的line2D对象使用fig的坐标,我们将fig.TransFigure赋给Line2D对象的transform属性;为了让line2D对象知道它是在fig对象中,我们还设置其figure属性为fig;最后还需要将创建的两个Line2D对象添加到fig.lines属性中去。

Figure对象有如下属性包含其他的Artist对象:

  • axes:Axes对象列表;
  • patch:作为背景的Rectangle对象;
  • images:FigureImage对象列表,用来显示图片;
  • legends:Legend(图例)对象列表;
  • lines:Line2D对象列表;
  • patchs:pacth对象列表;
  • texts:Text对象列表,用来显示文字;

Axes容器
Axes容器是整个matplotlib库的核心,它包含了自称众多Artist对象,并且有许多方法函数帮助我们创建、修改这些对象。和Figure一样,它有一个patch属性当作背景,当它是笛卡尔坐标时,patch属性是一个Rectangle对象,而它是极坐标时,patch属性则是Circle对象。
例如设置Axes对象的背景颜色为绿色,figure的背景为红色:

import matplotlib.pyplot as plt

fig=plt.figure()
fig.patch.set_color("r")
ax=fig.add_subplot(111)
ax.patch.set_facecolor("green")
plt.show()

当你调用Axes的绘图方法时,它将创建一组Line2D对象,并将所有的关键字参数传递给这个Line2D对象,并将它们添加进Axes.lines属性中,最后返回所创建的Line2D对象列表:

import numpy as np
x,y=np.random.rand(2,100)

line, =ax.plot(x,y,"-",color="blue",linewidth=2)
print(line)
# Line2D(_line0)

print(ax.lines)
# [<matplotlib.lines.Line2D object at 0x7f455617cf28>]

注意plot返回的是一个Line2D对象的列表,因为我们可以传递多组X,Y轴的数据,一次绘制多条曲线。
与plot方法类似,绘制直方图的方法bar和绘制柱状图的方法hist将创建一个Patch对象的列表,每个元素实际上都是Patch的子类Rectangle,并且将所创建的Patch对象都添加进Axes.patches属性中:

import matplotlib.pyplot as plt
import numpy as np

fig=plt.figure()

ax=fig.add_subplot(111)
n,bins,rects=ax.hist(np.random.randn(1000),50,facecolor="blue")


print(rects)
# <a list of 50 Patch objects>

print(rects[0])
# Rectangle(xy=(-3.23021, 0), width=0.123145, height=2, angle=0)

print(ax.patches[0])
# Rectangle(xy=(-3.31238, 0), width=0.12749, height=1, angle=0)

一般我们不会直接对Axes.lines或者Axes.patches属性进行操作,而是调用add_line或者add_patch等方法,这些方法帮助我们完成许多属性设置工作:

import matplotlib.pyplot as plt
import matplotlib

fig=plt.figure()
ax=fig.add_subplot(111)
rect=matplotlib.patches.Rectangle((1,1),width=5,height=12)

print(rect.get_transform()) #rect的transform属性为缺省值

"""
CompositeGenericTransform(
    BboxTransformTo(
        Bbox(x0=1.0, y0=1.0, x1=6.0, y1=13.0)),
    Affine2D(
        [[1. 0. 0.]
         [0. 1. 0.]
         [0. 0. 1.]]))
"""

#将rect添加进ax
ax.add_patch(rect)

#rect的transform属性和ax的transData相同
print(rect.get_transform())

print(ax.transData)

可以看出,add_patch方法帮助我们设置了rect的axes和transform属性。

  • artists:Artist对象列表;
  • patch:作为Axes背景的Patch对象,可以是Rectangle或者Circle;
  • collections:Collection对象列表;
  • images:AxesImage对象列表;
  • legends:Legend对象列表;
  • lines:Line2D对象列表;
  • patches:Patch对象列表;
  • texts:Text对象列表;
  • xaxis:XAxis对象;
  • yaxis:YAxis对象;

下面列出Axes的创建Artist对象的方法:

Axes的方法所创建的对象添加进的列表
annotate(注释)Annotatetexts
bars(柱形图)Rectanglepatches
errorbar(误差条形图)Line2D,Rectanglelines,patches
fillPolygonpatches
hist(直方图)Rectanglepatches
imshow(显示图形)AxesImageimages
legendLegendlegends
plotLine2Dlines
scatter(散点图)PolygonCollectioncollections
textTexttexts

实例散点图:

import matplotlib.pyplot as plt
import numpy as np

fig=plt.figure()

ax=fig.add_subplot(111)
t=ax.scatter(np.random.rand(20),np.random.rand(20))

# t的返回值为PathCollection对象
print(t)
# <matplotlib.collections.PathCollection object at 0x7f461d66df60>

#返回的对象已经添加进collections列表中
print(ax.collections)
# [<matplotlib.collections.PathCollection object at 0x7ff4a1ac7f28>]


plt.show()

在这里插入图片描述

Axis容器
Axis容器包括坐标轴上的刻度线、刻度文本、坐标网格以极坐标轴标题等内容。刻度包括主刻度和副刻度。分别通过Axis.get_major_ticks和Axis.get_minor_ticks方法获得。每个刻度线都是一个XTick或者YTick对象,它包括实际的刻度线和刻度文本。为了方便访问刻度线和文本,Axis对象提供了get_ticklabels和get_ticklines方法分别直接获得刻度线和刻度文本:

import matplotlib.pyplot as plt
import numpy as np

plt.plot([1,2,3],[4,5,6])
# plt.show()

axis=plt.gca().xaxis

#获取刻度的位置列表
print(axis.get_ticklocs())
# [0.75 1.   1.25 1.5  1.75 2.   2.25 2.5  2.75 3.   3.25]

#获得刻度标签列表
print(axis.get_ticklabels())
# <a list of 11 Text major ticklabel objects>

print([x.get_text() for x in axis.get_ticklabels()])


#获得主刻度线列表,图的上下刻度线共10条
print(axis.get_ticklines())
# <a list of 22 Line2D ticklines objects>

#获得副刻度线列表
print(axis.get_ticklines(minor=True))
# <a list of 0 Line2D ticklines objects>

获得刻度线标签之后,可以设置其各种属性。

for label in axis.get_ticklabels():
    label.set_color("red")
    label.set_rotation(45)
    label.set_fontsize(16)

for line in axis.get_ticklines():
    line.set_color("green")
    line.set_markersize(25)
    line.set_markeredgewidth(3)

plt.show()

在这里插入图片描述

>>> axis.get_minor_locator() # 计算副刻度的对象
<matplotlib.ticker.NullLocator instance at 0x0A014300>
>>> axis.get_major_locator() # 计算主刻度的对象
<matplotlib.ticker.AutoLocator instance at 0x09281B20>

我们可以使用程序为Axis对象设置不同的Locator对象,用来手工设置刻度的位置;设置Formatter对象用来控制刻度文本的显示。下面的程序设置X轴的主刻度以pi为单位:

#coding:utf-8

import matplotlib.pyplot as pl
from matplotlib.ticker import MultipleLocator,FuncFormatter
import numpy as np

x=np.arange(0,4*np.pi,0.01)
y=np.sin(x)

pl.figure(figsize=(8,4))
pl.plot(x,y)

ax=pl.gca()

def pi_formatter(x,pos):

    """将数值转换为以pi/4为单位的刻度文本"""

    m=np.round(x/(np.pi/4))
    n=4

    if m%2==0: m,n=m/2,n/2
    if m==0:
        return "0"
    if m==1 and n==1:
        return "$\pi$"
    if n==1:
        return r"$%d \pi$" %m
    if m==1:
        return r"$\frac{\pi}{%d}$" %n

    return r"$\frac{%d \pi}{%d}$" %(m,n)

#设置两个坐标轴的范围
pl.ylim(-1.5,1.5)
pl.xlim(0,np.max(x))

#设置图的底边距
pl.subplots_adjust(bottom=0.15)

pl.grid() #开启网格

#主格线为pi/4
ax.xaxis.set_major_locator(MultipleLocator(np.pi/4))

#主刻度文本用pi_formatter函数计算
ax.xaxis.set_major_formatter(FuncFormatter(pi_formatter))

#副刻度为pi/20
ax.xaxis.set_minor_locator(MultipleLocator(np.pi/20))

#设置刻度文本的大小
for tick in ax.xaxis.get_major_ticks():
    tick.label1.set_fontsize(16)

pl.show()

在这里插入图片描述

关于刻度的定位和文本格式的东西都在matploylib.ticker中定义,程序中使用到如下两个类:

  • MultipleLocator:以指定的整数倍为刻度线
  • FuncFormatter:使用指定的函数计算刻度文本,它会传递给所指定的函数两个参数:刻度值和刻度序号,程序通过比较笨的方法计算出刻度值所对应的刻度文本。
  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值