python - 运行时错误 : The init_func must return a sequence of Artist objects

标签 python matplotlib

我正在尝试在我的 jupyter notebook 上测试一个 Matplotlib 动画示例,如下所示:

from matplotlib import animation
# solve the ode problem of the double compound pendulum again

from scipy.integrate import odeint
from numpy import cos, sin

g = 9.82; L = 0.5; m = 0.1

def dx(x, t):
    x1, x2, x3, x4 = x[0], x[1], x[2], x[3]

    dx1 = 6.0/(m*L**2) * (2 * x3 - 3 * cos(x1-x2) * x4)/(16 - 9 * cos(x1-x2)**2)
    dx2 = 6.0/(m*L**2) * (8 * x4 - 3 * cos(x1-x2) * x3)/(16 - 9 * cos(x1-x2)**2)
    dx3 = -0.5 * m * L**2 * ( dx1 * dx2 * sin(x1-x2) + 3 * (g/L) * sin(x1))
    dx4 = -0.5 * m * L**2 * (-dx1 * dx2 * sin(x1-x2) + (g/L) * sin(x2))
    return [dx1, dx2, dx3, dx4]

x0 = [np.pi/2, np.pi/2, 0, 0]  # initial state
t = np.linspace(0, 10, 250) # time coordinates
x = odeint(dx, x0, t)    # solve the ODE problem

fig, ax = plt.subplots(figsize=(5,5))

ax.set_ylim([-1.5, 0.5])
ax.set_xlim([1, -1])

pendulum1, = ax.plot([], [], color="red", lw=2)
pendulum2, = ax.plot([], [], color="blue", lw=2)

def init():
    pendulum1.set_data([], [])
    pendulum2.set_data([], [])

def update(n): 
    # n = frame counter
    # calculate the positions of the pendulums
    x1 = + L * sin(x[n, 0])
    y1 = - L * cos(x[n, 0])
    x2 = x1 + L * sin(x[n, 1])
    y2 = y1 - L * cos(x[n, 1])

    # update the line data
    pendulum1.set_data([0 ,x1], [0 ,y1])
    pendulum2.set_data([x1,x2], [y1,y2])

anim = animation.FuncAnimation(fig, update, init_func=init, frames=len(t), blit=True)

# anim.save can be called in a few different ways, some which might or might not work
# on different platforms and with different versions of matplotlib and video encoders
#anim.save('animation.mp4', fps=20, extra_args=['-vcodec', 'libx264'], writer=animation.FFMpegWriter())
#anim.save('animation.mp4', fps=20, extra_args=['-vcodec', 'libx264'])
#anim.save('animation.mp4', fps=20, writer="ffmpeg", codec="libx264")
anim.save('animation.mp4', fps=20, writer="avconv", codec="libx264")

plt.close(fig)

但是,当我在 notebook 中运行单元格时,出现了这个错误:

RuntimeError: The init_func must return a sequence of Artist objects.

我不太确定发生了什么。我在 init 函数中没有看到任何错误。

此示例的链接:https://github.com/jrjohansson/scientific-python-lectures/blob/master/Lecture-4-Matplotlib.ipynb 它位于本笔记本的最底部。

最佳答案

正如错误所暗示的那样,并且可以看到例如在simple_animation example , 也来自 FuncAnimation documentation , init_func 以及更新的 func 应该返回一个可迭代的艺术家来制作动画。

文档中并没有说这实际上只有在使用blit=True 时才需要,但是既然你在这里使用blitting,那肯定是需要的。

因此您需要做的是让 init 函数以及 update 函数返回动画化的两行

def init():
    pendulum1.set_data([], [])
    pendulum2.set_data([], [])
    return pendulum1, pendulum2, 

def update(n): 
    # n = frame counter
    # calculate the positions of the pendulums
    x1 = + L * sin(x[n, 0])
    y1 = - L * cos(x[n, 0])
    x2 = x1 + L * sin(x[n, 1])
    y2 = y1 - L * cos(x[n, 1])

    # update the line data
    pendulum1.set_data([0 ,x1], [0 ,y1])
    pendulum2.set_data([x1,x2], [y1,y2])

    return pendulum1, pendulum2, 

关于python - 运行时错误 : The init_func must return a sequence of Artist objects,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/45091682/

相关文章:

python - 通过临时变量对 Pandas 数据框中的值进行排序

python - 在 Django 中使用 POST 的参数显示 matplotlib 生成的多张图片

python - 我想从子进程中获取 stdout 和 stderr

python - 将 matplotlib 3D 图形的框架更改为 x、y 和 z 箭头

python - 子图中 seaborn 热图的一个颜色条

python - 将值从html模板传递到Django中的views.py

python - 对 NumPy 数组执行运算,但从这些运算中屏蔽沿对角线的值

python - 如何围绕散点图上的一个点绘制圆环图?

python - 如何按月创建最小-最大线图

python - 如何减少 Python 绘图中的空白?