为多个子图设置具有固定指数和有效数字的科学记数法
Set scientific notation with fixed exponent and significant digits for multiple subplots
我正在尝试将轴固定为两组不同数据的科学记数法,其中一组是 [1-9]x1e-3,另一组是 [1-9]x1e-4。我想将两个轴都设置为 10^-4 并在小数点后有一位数字(例如 %.1e)。这是我尝试过的一个简单版本:我希望轴上的数字至少为 1,并且我希望两个幂相同。
import numpy as np
import matplotlib.pyplot as plt
x = np.linspace(1,9,9)
y1 = x*10**(-4)
y2 = x*10**(-3)
fig, ax = plt.subplots(2,1,sharex=True)
ax[0].plot(x,y1)
ax[0].ticklabel_format(axis='y', style='sci', scilimits=(-4,-4))
ax[0].yaxis.major.formatter._useMathText = True
ax[1].plot(x,y2)
ax[1].ticklabel_format(axis='y', style='sci', scilimits=(-4,-4))
ax[1].yaxis.major.formatter._useMathText = True
plt.show()
您可以子class matplotlib.ticker.ScalarFormatter
并将orderOfMagnitude
属性固定为您喜欢的数字(在本例中为-4
)。
以同样的方式,您可以修复要使用的格式。
import numpy as np
import matplotlib.pyplot as plt
import matplotlib.ticker
class OOMFormatter(matplotlib.ticker.ScalarFormatter):
def __init__(self, order=0, fformat="%1.1f", offset=True, mathText=True):
self.oom = order
self.fformat = fformat
matplotlib.ticker.ScalarFormatter.__init__(self,useOffset=offset,useMathText=mathText)
def _set_order_of_magnitude(self):
self.orderOfMagnitude = self.oom
def _set_format(self, vmin=None, vmax=None):
self.format = self.fformat
if self._useMathText:
self.format = r'$\mathdefault{%s}$' % self.format
x = np.linspace(1,9,9)
y1 = x*10**(-4)
y2 = x*10**(-3)
fig, ax = plt.subplots(2,1,sharex=True)
ax[0].plot(x,y1)
ax[1].plot(x,y2)
for axe in ax:
axe.yaxis.set_major_formatter(OOMFormatter(-4, "%1.1f"))
axe.ticklabel_format(axis='y', style='sci', scilimits=(-4,-4))
plt.show()
虽然乍一看这似乎很复杂,但它真正做的唯一事情是覆盖私有方法 _set_orderOfMagnitude
和 _set_format
,从而防止它们在后台做一些我们不做的复杂事情'想要。因为最后,我们所需要的只是,与内部发生的事情无关,self.orderOfMagnitude
总是 -4
而 self.format
总是 "%1.1f"
.
注意:在 matplotlib < 3.1 中,class 需要看起来像
class OOMFormatter(matplotlib.ticker.ScalarFormatter):
def __init__(self, order=0, fformat="%1.1f", offset=True, mathText=True):
self.oom = order
self.fformat = fformat
matplotlib.ticker.ScalarFormatter.__init__(self,useOffset=offset,useMathText=mathText)
def _set_orderOfMagnitude(self, nothing=None):
self.orderOfMagnitude = self.oom
def _set_format(self, vmin=None, vmax=None):
self.format = self.fformat
if self._useMathText:
self.format = '$%s$' % matplotlib.ticker._mathdefault(self.format)
我正在尝试将轴固定为两组不同数据的科学记数法,其中一组是 [1-9]x1e-3,另一组是 [1-9]x1e-4。我想将两个轴都设置为 10^-4 并在小数点后有一位数字(例如 %.1e)。这是我尝试过的一个简单版本:我希望轴上的数字至少为 1,并且我希望两个幂相同。
import numpy as np
import matplotlib.pyplot as plt
x = np.linspace(1,9,9)
y1 = x*10**(-4)
y2 = x*10**(-3)
fig, ax = plt.subplots(2,1,sharex=True)
ax[0].plot(x,y1)
ax[0].ticklabel_format(axis='y', style='sci', scilimits=(-4,-4))
ax[0].yaxis.major.formatter._useMathText = True
ax[1].plot(x,y2)
ax[1].ticklabel_format(axis='y', style='sci', scilimits=(-4,-4))
ax[1].yaxis.major.formatter._useMathText = True
plt.show()
您可以子class matplotlib.ticker.ScalarFormatter
并将orderOfMagnitude
属性固定为您喜欢的数字(在本例中为-4
)。
以同样的方式,您可以修复要使用的格式。
import numpy as np
import matplotlib.pyplot as plt
import matplotlib.ticker
class OOMFormatter(matplotlib.ticker.ScalarFormatter):
def __init__(self, order=0, fformat="%1.1f", offset=True, mathText=True):
self.oom = order
self.fformat = fformat
matplotlib.ticker.ScalarFormatter.__init__(self,useOffset=offset,useMathText=mathText)
def _set_order_of_magnitude(self):
self.orderOfMagnitude = self.oom
def _set_format(self, vmin=None, vmax=None):
self.format = self.fformat
if self._useMathText:
self.format = r'$\mathdefault{%s}$' % self.format
x = np.linspace(1,9,9)
y1 = x*10**(-4)
y2 = x*10**(-3)
fig, ax = plt.subplots(2,1,sharex=True)
ax[0].plot(x,y1)
ax[1].plot(x,y2)
for axe in ax:
axe.yaxis.set_major_formatter(OOMFormatter(-4, "%1.1f"))
axe.ticklabel_format(axis='y', style='sci', scilimits=(-4,-4))
plt.show()
虽然乍一看这似乎很复杂,但它真正做的唯一事情是覆盖私有方法 _set_orderOfMagnitude
和 _set_format
,从而防止它们在后台做一些我们不做的复杂事情'想要。因为最后,我们所需要的只是,与内部发生的事情无关,self.orderOfMagnitude
总是 -4
而 self.format
总是 "%1.1f"
.
注意:在 matplotlib < 3.1 中,class 需要看起来像
class OOMFormatter(matplotlib.ticker.ScalarFormatter):
def __init__(self, order=0, fformat="%1.1f", offset=True, mathText=True):
self.oom = order
self.fformat = fformat
matplotlib.ticker.ScalarFormatter.__init__(self,useOffset=offset,useMathText=mathText)
def _set_orderOfMagnitude(self, nothing=None):
self.orderOfMagnitude = self.oom
def _set_format(self, vmin=None, vmax=None):
self.format = self.fformat
if self._useMathText:
self.format = '$%s$' % matplotlib.ticker._mathdefault(self.format)