Python 3.x 如何在Matplotlib中设置轴的视图/范围限制

Python 3.x 如何在Matplotlib中设置轴的视图/范围限制,python-3.x,matplotlib,Python 3.x,Matplotlib,我想在轴上最后一个勾号位置前后留出一些空间。例如,我只想使用axis.set_xlim(),但这会干扰我的(自定义)定位器并重新运行记号生成。我找到并覆盖了定位器类的view\u limits()方法,但它们似乎不会被自动调用,当手动调用时,它们不会对生成的绘图产生任何影响。我搜索了文档和源代码,但没有找到解决方案。我错过什么了吗 对于更大的图片,我希望有一个定位器,它在刻度前后给我一些空间,并选择刻度点,这些刻度点是“基准”的倍数,就像MultipleLocator一样,但如果刻度数超过指定值

我想在轴上最后一个勾号位置前后留出一些空间。例如,我只想使用axis.set_xlim(),但这会干扰我的(自定义)定位器并重新运行记号生成。我找到并覆盖了定位器类的
view\u limits()
方法,但它们似乎不会被自动调用,当手动调用时,它们不会对生成的绘图产生任何影响。我搜索了文档和源代码,但没有找到解决方案。我错过什么了吗

对于更大的图片,我希望有一个定位器,它在刻度前后给我一些空间,并选择刻度点,这些刻度点是“基准”的倍数,就像MultipleLocator一样,但如果刻度数超过指定值,则会自动缩放基准。如果有另一种方法可以实现这一点,而无需对定位器进行子类化,我洗耳恭听:)

下面是我的示例代码,用于覆盖
视图\u限制的子类定位器
-方法:

import matplotlib.pyplot as plt
import numpy as np
from matplotlib.ticker import MaxNLocator

class MyLocator(MaxNLocator):
    def __init__(self, *args, **kwargs):
        super().__init__(*args, **kwargs)

    def view_limits(self, dmin, dmax):
        bins = self.bin_boundaries(dmin, dmax)
        step = bins[1] - bins[0]
        result = np.array([bins[0] - step, bins[-1] + step])
        print(result)
        return result

a = 10.0
b = 99.0

t = np.arange(a, b, 0.1)
s = np.sin(0.1*np.pi*t)*np.exp(-t*0.01)

loc = MyLocator(9)

fig, ax = plt.subplots()
plt.plot(t, s)

ax.xaxis.set_major_locator(loc)
loc.autoscale()  # results in [   0.  110.] but doesnt change the plot
plt.show()

不确定,如果我完全理解您的问题所在,但如果您只想添加额外的空间,您仍然可以使用MaxNLocator手动添加该空间,如下所示:

import matplotlib.pyplot as plt
import numpy as np
from matplotlib.ticker import MaxNLocator

a = 10.0
b = 99.0

t = np.arange(a, b, 0.1)
s = np.sin(0.1*np.pi*t)*np.exp(-t*0.01)

loc = MaxNLocator(9)

fig, ax = plt.subplots()
plt.plot(t, s)

ax.xaxis.set_major_locator(loc)
ticks = ax.get_xticks()
newticks = np.zeros(len(ticks)+2)
newticks[0] = ticks[0]- (ticks[1]-ticks[0])
newticks[-1] = ticks[-1]+ (ticks[1]-ticks[0])
newticks[1:-1] = ticks
ax.set_xticks(newticks)

plt.show()

不确定,如果我完全理解您的问题所在,但如果您只想添加额外的空间,您仍然可以使用MaxNLocator手动添加该空间,如下所示:

import matplotlib.pyplot as plt
import numpy as np
from matplotlib.ticker import MaxNLocator

a = 10.0
b = 99.0

t = np.arange(a, b, 0.1)
s = np.sin(0.1*np.pi*t)*np.exp(-t*0.01)

loc = MaxNLocator(9)

fig, ax = plt.subplots()
plt.plot(t, s)

ax.xaxis.set_major_locator(loc)
ticks = ax.get_xticks()
newticks = np.zeros(len(ticks)+2)
newticks[0] = ticks[0]- (ticks[1]-ticks[0])
newticks[-1] = ticks[-1]+ (ticks[1]-ticks[0])
newticks[1:-1] = ticks
ax.set_xticks(newticks)

plt.show()

下面是一个略显粗糙的解决方案,用于避免靠近绘图边缘的记号:

class PaddedMaxNLocator(mp.ticker.MaxNLocator):
    def __init__(self, *args, protected_width=0.25, **kwargs):
        # `prune` edge ticks that might now become visible
        super().__init__(*args, **kwargs, prune='both')
        # Clamp to some reasonable range
        self.protected_width = min(0.5, protected_width)

    def tick_values(self, vmin, vmax):
        diff = (vmax - vmin) * self.protected_width / 2
        return super().tick_values(vmin + diff, vmax - diff)

下面是一个略显粗糙的解决方案,用于避免靠近绘图边缘的记号:

class PaddedMaxNLocator(mp.ticker.MaxNLocator):
    def __init__(self, *args, protected_width=0.25, **kwargs):
        # `prune` edge ticks that might now become visible
        super().__init__(*args, **kwargs, prune='both')
        # Clamp to some reasonable range
        self.protected_width = min(0.5, protected_width)

    def tick_values(self, vmin, vmax):
        diff = (vmax - vmin) * self.protected_width / 2
        return super().tick_values(vmin + diff, vmax - diff)

谢谢你的把戏!我可以这样做。我还是想知道为什么整个视图方法不能像预期的那样工作。谢谢你的技巧!我可以这样做。我还是想知道为什么整个视图方法不能像预期的那样工作。