我熟悉以下问题:
Matplotlib savefig with a legend outside the plot
How to put the legend out of the plot
似乎这些问题的答案能够摆弄轴的精确缩小以使图例适合。
然而,缩小坐标轴并不是一个理想的解决方案,因为它会使数据变得更小,从而实际上更难以解释;特别是当它很复杂并且有很多事情发生时......因此需要一个大的传说
文档中的复杂图例示例说明了这样做的必要性,因为图中的图例实际上完全掩盖了多个数据点。
http://matplotlib.sourceforge.net/users/legend_guide.html#legend-of-complex-plots
我希望能够动态扩展图形框的大小以适应扩展图形图例。
import matplotlib.pyplot as plt
import numpy as np
x = np.arange(-2*np.pi, 2*np.pi, 0.1)
fig = plt.figure(1)
ax = fig.add_subplot(111)
ax.plot(x, np.sin(x), label='Sine')
ax.plot(x, np.cos(x), label='Cosine')
ax.plot(x, np.arctan(x), label='Inverse tan')
lgd = ax.legend(loc=9, bbox_to_anchor=(0.5,0))
ax.grid('on')
请注意最终标签“反棕褐色”实际上是如何在图形框之外的(并且看起来很严重 - 不是出版质量!)
最后,有人告诉我这是 R 和 LaTeX 中的正常行为,所以我有点困惑为什么这在 python 中如此困难......有历史原因吗? Matlab 在这件事上是否同样糟糕?
我在 pastebin http://pastebin.com/grVjc007 上有这个代码的(只是稍微)更长的版本
最佳答案
抱歉 EMS,但实际上我刚刚收到了来自 matplotlib 邮件列表的另一个回复(感谢 Benjamin Root)。
我正在寻找的代码正在将 savefig 调用调整为:
fig.savefig('samplefigure', bbox_extra_artists=(lgd,), bbox_inches='tight')
#Note that the bbox_extra_artists must be an iterable
这显然类似于调用tight_layout,但您允许savefig 在计算中考虑额外的艺术家。实际上,这确实根据需要调整了图形框的大小。
import matplotlib.pyplot as plt
import numpy as np
plt.gcf().clear()
x = np.arange(-2*np.pi, 2*np.pi, 0.1)
fig = plt.figure(1)
ax = fig.add_subplot(111)
ax.plot(x, np.sin(x), label='Sine')
ax.plot(x, np.cos(x), label='Cosine')
ax.plot(x, np.arctan(x), label='Inverse tan')
handles, labels = ax.get_legend_handles_labels()
lgd = ax.legend(handles, labels, loc='upper center', bbox_to_anchor=(0.5,-0.1))
text = ax.text(-0.2,1.05, "Aribitrary text", transform=ax.transAxes)
ax.set_title("Trigonometry")
ax.grid('on')
fig.savefig('samplefigure', bbox_extra_artists=(lgd,text), bbox_inches='tight')
这会产生:
[编辑] 这个问题的目的是完全避免使用任意文本的任意坐标位置,因为这是这些问题的传统解决方案。尽管如此,最近的许多编辑都坚持将它们放入,通常以导致代码引发错误的方式。我现在已经解决了这些问题并整理了任意文本,以展示如何在 bbox_extra_artists 算法中考虑这些问题。
https://stackoverflow.com/questions/10101700/