- 在PyCharm,Ipython以及Jupyter-notebook中不能正常显示,这是由于IDE的相关配置没有做好,均可以在网上查到相关配置方法,在此不做赘述。
- 在IDE配置好的情况下,动画不显示。
官方示例:
import numpy as np
import matplotlib.pyplot as plt
from matplotlib.animation import FuncAnimation
fig, ax = plt.subplots()
xdata, ydata = [], []
ln, = plt.plot([], [], 'ro')
def init():
ax.set_xlim(0, 2*np.pi)
ax.set_ylim(-1, 1)
return ln,
def update(frame):
xdata.append(frame)
ydata.append(np.sin(frame))
ln.set_data(xdata, ydata)
print(frame)
return ln,
ani = FuncAnimation(fig, update, frames=np.linspace(0, 2*np.pi, 128),
init_func=init, blit=True)
plt.show()
效果正常。
现在我们来把代码进行一下改动.
import numpy as np
import matplotlib.pyplot as plt
from matplotlib.animation import FuncAnimation
fig, ax = plt.subplots()
xdata, ydata = [], []
ln, = plt.plot([], [], 'ro')
def init():
ax.set_xlim(0, 2*np.pi)
ax.set_ylim(-1, 1)
return ln,
def update(frame):
xdata.append(frame)
ydata.append(np.sin(frame))
ln.set_data(xdata, ydata)
print(frame)
return ln,
FuncAnimation(fig, update, frames=np.linspace(0, 2*np.pi, 128),
init_func=init, blit=True)
plt.show()
可以看到,代码失效了,没有任何动画出现。而唯一的改动在于,倒数第二句代码由
ani = FuncAnimation(fig, update, frames=np.linspace(0, 2*np.pi, 128),init_func=init, blit=True)
变为
FuncAnimation(fig, update, frames=np.linspace(0, 2*np.pi, 128),init_func=init, blit=True)
这个问题,参见issue1656,以及官方文档的说明。简而言之,就是如果不是显式声明,即通过 ani = FuncAnimation() 赋值,Python的垃圾回收机制就会将这个动画引用删除。所以最简单的方式就是通过ani = FuncAnimation() 的方式来保存动画。
当然,对于正常的过程式代码使用时,可以通过这种方式解决作图问题,那么如果是想把作图包装成一个函数呢?
- 在函数内提供返回值,返回FuncAnimation 后再引用。但是当此函数再被嵌入到另外一个函数中的时候,该方法就失效了。
- 定义全局变量,用全局变量保存FuncAnimation 的引用。
global anim
def return_anim():
anim = animation.FuncAnimation(fig, animate, blit=True)
return anim
def use_ani():
global anim
anim = return_anim()
use_ani()