【问题标题】:How to update Matplotlib graph when new data arrives?新数据到达时如何更新 Matplotlib 图?
【发布时间】:2021-09-22 06:49:49
【问题描述】:

我正在构建一个机器人,它每 30 秒从互联网上获取数据。

我想使用 matplotlib 绘制这些数据,并在我获取一些新数据时能够更新图表。

在脚本的开头,我初始化了我的情节。 然后我运行一个函数每 30 秒更新一次这些绘图,但此时我的绘图窗口冻结了。

我做了一些研究,但似乎找不到任何可行的解决方案:

plt.show(block=False)
plt.pause(0.001)

我做错了什么?

代码的一般结构:

import matplotlib.pyplot as plt
import time

def init_plots():
    global fig
    global close_line

    plt.ion()
    fig = plt.figure()
    main_fig = fig.add_subplot(111)

    x = [datetime.fromtimestamp(x) for x in time_series]
    close_line, = main_fig.plot(x, close_history, 'k-')
    plt.draw()


def update_all_plots():
    global close_line

    x = [datetime.fromtimestamp(x) for x in time_series]

    close_line.set_xdata(time_series)
    close_line.set_ydata(close_history)

    plt.draw()


# SCRIPT :
init_plots()
while(True):
     # Fetch new data...
     # Update time series...
     # Update close_history...
     update_plots()
     time.sleep(30)

【问题讨论】:

    标签: python matplotlib


    【解决方案1】:

    matplotlib 中有一个模块专门用于随时间变化的绘图:https://matplotlib.org/api/animation_api.html

    基本上你定义一个更新函数,更新你的线对象的数据。然后可以使用该更新函数创建一个 FuncAnimation 对象,该对象每 x 毫秒自动调用一次更新函数:

    ani = FuncAnimation(figure, update_function, repeat=True, interval=x)
    

    【讨论】:

    • 感谢您的回复。我是否应该在另一个线程上绘制图表,以便我的主脚本可以继续而不会被绘图阻塞?
    • 绘图中唯一的阻塞部分是plt.show() 函数。我通常会启动一个单独的线程,将数据输入绘图,然后从我的主脚本中调用plt.show()。所以我的主脚本一直阻塞,直到情节关闭,但数据源不断提供数据。但是我想如果启用交互模式,您可以使主脚本不阻塞:matplotlib.org/faq/usage_faq.html#what-is-interactive-mode
    • 我如何在我的 python 脚本休眠时保持我的情节不冻结(使用 time.sleep(x))?
    【解决方案2】:

    有一个简单的方法可以做到这一点,给定一个熊猫数据框。你通常会做这样的事情来绘制(df是数据框):

    ax = df.plot.line()

    使用

    df.plot.line(reuse_plot=True,ax=ax)

    人们可以重复使用相同的图形来优雅地重新绘制它,并且可能足够快。

    可能与Matplotlib updating live plot 重复

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2019-06-04
      • 2012-06-29
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多