python matplotlib从函数更新散点图

2025-02-14 09:49:00
admin
原创
39
摘要:问题描述:我正在尝试自动更新散点图。我的 X 和 Y 值的来源是外部的,并且数据会在非预测的时间间隔(轮次)内自动推送到我的代码中。我仅设法在整个过程结束时绘制所有数据,而我正尝试不断地将数据添加和绘制到画布中。我得到的(在整个运行结束时)是这样的:然而,我想要的是这个:我的代码的简化版本:import ma...

问题描述:

我正在尝试自动更新散点图。我的 X 和 Y 值的来源是外部的,并且数据会在非预测的时间间隔(轮次)内自动推送到我的代码中。

我仅设法在整个过程结束时绘制所有数据,而我正尝试不断地将数据添加和绘制到画布中。

我得到的(在整个运行结束时)是这样的:
在此处输入图片描述

然而,我想要的是这个:
在此处输入图片描述

我的代码的简化版本:

import matplotlib.pyplot as plt

def read_data():
    #This function gets the values of xAxis and yAxis
    xAxis = [some values]  #these valuers change in each run
    yAxis = [other values] #these valuers change in each run

    plt.scatter(xAxis,yAxis, label  = 'myPlot', color = 'k', s=50)     
    plt.xlabel('x')
    plt.ylabel('y')
    plt.show()

解决方案 1:

有几种方法可以为 matplotlib 图制作动画。下面让我们看两个使用散点图的最小示例。

(a)使用交互模式plt.ion()

要使动画发生,我们需要一个事件循环。获取事件循环的一种方法是使用plt.ion()(“interactive on”)。然后需要先绘制图形,然后可以在循环中更新绘图。在循环中,我们需要绘制画布并引入一个短暂的暂停,以便窗口处理其他事件(如鼠标交互等)。如果没有这个暂停,窗口就会冻结。最后,我们调用plt.waitforbuttonpress()让窗口在动画结束后保持打开状态。

import matplotlib.pyplot as plt
import numpy as np

plt.ion()
fig, ax = plt.subplots()
x, y = [],[]
sc = ax.scatter(x,y)
plt.xlim(0,10)
plt.ylim(0,10)

plt.draw()
for i in range(1000):
    x.append(np.random.rand(1)*10)
    y.append(np.random.rand(1)*10)
    sc.set_offsets(np.c_[x,y])
    fig.canvas.draw_idle()
    plt.pause(0.1)

plt.waitforbuttonpress()

(b)使用FuncAnimation

上述大部分操作均可使用 实现自动化matplotlib.animation.FuncAnimation。FuncAnimation 将负责循环和重绘,并animate()在给定的时间间隔后不断调用函数(在本例中为 )。动画仅在plt.show()调用后启动,从而自动在绘图窗口的事件循环中运行。

import matplotlib.pyplot as plt
import matplotlib.animation
import numpy as np

fig, ax = plt.subplots()
x, y = [],[]
sc = ax.scatter(x,y)
plt.xlim(0,10)
plt.ylim(0,10)

def animate(i):
    x.append(np.random.rand(1)*10)
    y.append(np.random.rand(1)*10)
    sc.set_offsets(np.c_[x,y])

ani = matplotlib.animation.FuncAnimation(fig, animate, 
                frames=2, interval=100, repeat=True) 
plt.show()

解决方案 2:

据我了解,您希望以交互方式更新您的图。 如果是这样,您可以使用图而不是散点图,并像这样更新图的数据。

import numpy
import matplotlib.pyplot as plt 
fig = plt.figure()
axe = fig.add_subplot(111)
X,Y = [],[]
sp, = axe.plot([],[],label='toto',ms=10,color='k',marker='o',ls='')
fig.show()
for iter in range(5):
    X.append(numpy.random.rand())
    Y.append(numpy.random.rand())
    sp.set_data(X,Y)
    axe.set_xlim(min(X),max(X))
    axe.set_ylim(min(Y),max(Y))
    raw_input('...')
    fig.canvas.draw()

如果这是您想要的行为,那么您只需要创建一个附加 sp 数据的函数,然后在该函数中获取您想要绘制的新点(使用 I/O 管理或您正在使用的任何通信过程)。希望这对您有所帮助。

解决方案 3:

这是在 Jupyter 笔记本中创建交互式绘图的一种方法

# Import Libraries

import numpy as np
import matplotlib.pyplot as plt
from IPython.display import display, clear_output

# Create figure and subplot

fig = plt.figure()
ax = fig.add_subplot(1, 1, 1) 

# Define and update plot

for i in range(20):
    x = np.linspace(0, i, 100);
    y = np.cos(x) 
    ax.set_xlim(0, i)    
    ax.cla()
    ax.plot(x, y)
    display(fig)    
    clear_output(wait = True)
    plt.pause(0.1)

这将迭代更新同一图。此处提供了详细说明https://pythonguides.com/matplotlib-update-plot-in-loop/

解决方案 4:

使用point.set_offsets(np.c_[xdata,ydata])对我有用,因为当我更新到 matplotlib 3.9 时,ax.set_data 停止工作。

外观:
1

import matplotlib.pyplot as plt 
import numpy as np

import matplotlib.animation as animation

def lerp(p0: np.array, p1: np.array,t = None,res=10):
    # t = np.array(t)
    if t == None: 
        t = np.linspace(0,1,res)
    outX = (1-t)*p0[0]+t*p1[0]
    outY = (1-t)*p0[1]+t*p1[1]
    return outX,outY


def lerpAnimation(p0: np.array, p1: np.array,res = 10,speed=100):
    plt.ioff()
    xdata, ydata = [0],[0]
    fig, ax = plt.subplots()
    point = ax.scatter(xdata, ydata, lw=2)
    ax.grid()
    firstLerp = lerp(p0,p1)

    ax.plot(firstLerp[0],firstLerp[1])
    def run(t):
        timedLerp = lerp(p0,p1,t)
        xdata[0], ydata[0] = timedLerp[0],timedLerp[1]
        # Here is where the values are changed
        point.set_offsets(np.c_[xdata,ydata])

        return point,

    ani = animation.FuncAnimation(fig, run, (i for i in np.linspace(0,1,res)), interval=speed,
                                    save_count=100,repeat = True)
    plt.show()
相关推荐
  政府信创国产化的10大政策解读一、信创国产化的背景与意义信创国产化,即信息技术应用创新国产化,是当前中国信息技术领域的一个重要发展方向。其核心在于通过自主研发和创新,实现信息技术应用的自主可控,减少对外部技术的依赖,并规避潜在的技术制裁和风险。随着全球信息技术竞争的加剧,以及某些国家对中国在科技领域的打压,信创国产化显...
工程项目管理   1565  
  为什么项目管理通常仍然耗时且低效?您是否还在反复更新电子表格、淹没在便利贴中并参加每周更新会议?这确实是耗费时间和精力。借助软件工具的帮助,您可以一目了然地全面了解您的项目。如今,国内外有足够多优秀的项目管理软件可以帮助您掌控每个项目。什么是项目管理软件?项目管理软件是广泛行业用于项目规划、资源分配和调度的软件。它使项...
项目管理软件   1354  
  信创国产芯片作为信息技术创新的核心领域,对于推动国家自主可控生态建设具有至关重要的意义。在全球科技竞争日益激烈的背景下,实现信息技术的自主可控,摆脱对国外技术的依赖,已成为保障国家信息安全和产业可持续发展的关键。国产芯片作为信创产业的基石,其发展水平直接影响着整个信创生态的构建与完善。通过不断提升国产芯片的技术实力、产...
国产信创系统   21  
  信创生态建设旨在实现信息技术领域的自主创新和安全可控,涵盖了从硬件到软件的全产业链。随着数字化转型的加速,信创生态建设的重要性日益凸显,它不仅关乎国家的信息安全,更是推动产业升级和经济高质量发展的关键力量。然而,在推进信创生态建设的过程中,面临着诸多复杂且严峻的挑战,需要深入剖析并寻找切实可行的解决方案。技术创新难题技...
信创操作系统   27  
  信创产业作为国家信息技术创新发展的重要领域,对于保障国家信息安全、推动产业升级具有关键意义。而国产芯片作为信创产业的核心基石,其研发进展备受关注。在信创国产芯片的研发征程中,面临着诸多复杂且艰巨的难点,这些难点犹如一道道关卡,阻碍着国产芯片的快速发展。然而,科研人员和相关企业并未退缩,积极探索并提出了一系列切实可行的解...
国产化替代产品目录   28  
热门文章
项目管理软件有哪些?
云禅道AD
禅道项目管理软件

云端的项目管理软件

尊享禅道项目软件收费版功能

无需维护,随时随地协同办公

内置subversion和git源码管理

每天备份,随时转为私有部署

免费试用