【问题标题】:matplotlib figures disappearing between show() and savefig()matplotlib 数字在 show() 和 savefig() 之间消失
【发布时间】:2016-07-26 17:10:57
【问题描述】:

我在字典中保存了一组对数字的引用,以便以后可以根据需要保存它们。如果调用show() 命令并先查看它们,我很担心保存的数字是空白的。由于show() 命令阻塞并且我没有使用类似spyder 的解释器,因此我必须在到达savefig() 之前关闭这些数字

figures['myfig_1'] = figure()
...
figures['myfig_n'] = figure()
...

#show() #disabling this makes the problem go away
print "Saving:"
for fig in figures:
   figure(figures[fig].number)
   savefig(fig)
   print "Figure " + str(figures[fig].number) + ": " + fig

这里的打印语句告诉我字典仍然完好无损,我认为这意味着我没有丢失数字引用(它们仍在其.number 属性中返回有意义的数字。)

我注意到的另一个转折是,当我在一个类中做了类似的事情,将字典存储为成员并将存储和保存函数划分为它们自己的方法时,这种情况不会发生。我关闭数据或存储数据的方式是否导致数据丢失?

【问题讨论】:

  • 我想出了一个答案,但我在 8 小时内无法添加它。老鼠...简短的版本是我现在将渲染后端更改为“TkAgg”,直到我能弄清楚如何让 Qt4Agg 以我想要的方式运行。

标签: python matplotlib


【解决方案1】:

一般来说,在这种情况下,不要使用交互式 matlab-ish 状态机接口来连接 matplotlib。它旨在用于交互式使用。

您正在尝试使人物“活跃”,并改为创建一个新人物。如果您只保留返回的图形和/或轴对象并直接使用它们,则哪个图形处于活动状态并不重要。 (另外,不要使用通配符导入!您在以后维护代码时后悔!)

只要做这样的事情:

import matplotlib.pyplot as plt
figures = {}

figures['a'] = plt.figure()
ax = figures['a'].add_subplot(111)
ax.plot(range(10), 'ro-')

figures['b'] = plt.figure()
ax = figures['b'].add_subplot(111)
ax.plot(range(10), 'bo-')

plt.show()

for name, fig in figures.iteritems():
    fig.savefig('figure-%s.png' % name)

【讨论】:

  • 我的新鲜事在这里出现,我什至不知道有这样一种巧妙的方法可以同时迭代键和值。我也同意通配符导入问题。我在一个新的环境中,有着“完成任务”的文化。除了打开名称冲突的可能性之外,它还使了解功能的来源变得更加困难。
  • 我改变了我的方式,现在使用 .iteritems() 方法,但我遇到了同样的问题:在 show() 之后,我关闭后似乎删除了数字交互式窗口。解释器在 .savefig 命令上停止,并通过 print_figure.draw() draw.update() 的调用堆栈告诉我底层 c/c++ 对象已被删除。
  • “状态机”方法似乎有效。如果没有 pyplot.show(),则会正确调用和保存数字。如果它们被显示,然后关闭,那么它们就丢失了。我不知道这是否是 pyplot.show() 意图的一部分,但这似乎是正在发生的事情。我不知道这是否是一个因素,但我正在导入一个名为 pylab 的包,我认为它给了我 pyplot,但我真的不知道。
【解决方案2】:

documentation开始,绘图元素是否从show()销毁取决于backend,以及matplotlib的版本。 1.1.0 版似乎没有破坏数字。要找出which backend is in use,请使用get_backend() 函数。就我而言,我使用的是 Qt4Agg 后端。通过调用 TkAgg 后端,调用 matplotlib.use('TkAgg'),这些数字在保存之前没有被破坏。现在来了解如何改变 Qt4Agg 的行为...

【讨论】:

  • 不错!我没有意识到...我使用的后端(主要是 TkAgg)在您调用 show 时不会破坏图形。我不知道有些人这样做了。当你打电话给figure(figures[fig].number) 时,我只是假设你正在清除这个数字。无论如何,我确实发现坚持使用 OO 界面而不依赖于激活图形要容易得多。
  • 顺便说一句,您可能应该将您的答案标记为更正,因为您解决了自己的问题。这样做是完全可以接受的,但我相信您必须等待 2 天才能将自己的答案标记为已接受。
  • 是的,它告诉我我还有 23 小时来标记自己的答案。
猜你喜欢
  • 1970-01-01
  • 2012-10-21
  • 2011-12-15
  • 1970-01-01
  • 2015-09-18
  • 2022-01-01
  • 2018-01-12
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多