Python中如何使用matplotlib animation实现曲线积分面积的动态填充?
小弟初学 PYTHON,想用 matplotlib 里的动画功能实现正态分布曲线在-3sigma 到+3sigma 积分面积的填充,当 sigma 变化时,曲线和填充面积也跟随变化的动图。目前做出了曲线随着 sigma 变化的动图,但填充面积无法实现,求大神指点迷津
Python中如何使用matplotlib animation实现曲线积分面积的动态填充?
1 回复
import numpy as np
import matplotlib.pyplot as plt
from matplotlib.animation import FuncAnimation
from matplotlib.patches import Polygon
# 定义被积函数
def f(x):
return np.sin(x) + 2
# 积分区间
a, b = 0, 2*np.pi
n_frames = 50 # 动画帧数
# 创建图形和坐标轴
fig, ax = plt.subplots(figsize=(10, 6))
x = np.linspace(a, b, 200)
y = f(x)
# 绘制原始曲线
ax.plot(x, y, 'b-', linewidth=2, label='f(x) = sin(x) + 2')
ax.fill_between(x, 0, y, alpha=0.2, color='gray') # 静态填充作为参考
ax.set_xlabel('x')
ax.set_ylabel('f(x)')
ax.set_title('曲线积分面积动态填充')
ax.legend()
ax.grid(True, alpha=0.3)
# 初始化填充多边形(开始时为空)
polygon = Polygon([], closed=True, alpha=0.5, color='orange')
ax.add_patch(polygon)
# 积分值文本
integral_text = ax.text(0.02, 0.95, '', transform=ax.transAxes, fontsize=12,
bbox=dict(boxstyle='round', facecolor='wheat', alpha=0.8))
def init():
"""初始化动画"""
polygon.set_xy([])
integral_text.set_text('')
return polygon, integral_text
def update(frame):
"""更新每一帧"""
# 当前积分上限(从a逐渐增加到b)
current_b = a + (b - a) * (frame + 1) / n_frames
# 计算当前积分值
x_current = np.linspace(a, current_b, 100)
y_current = f(x_current)
integral_value = np.trapz(y_current, x_current)
# 更新填充区域
vertices = [(a, 0)] + list(zip(x_current, y_current)) + [(current_b, 0)]
polygon.set_xy(vertices)
# 更新积分值文本
integral_text.set_text(f'∫f(x)dx ≈ {integral_value:.4f}\n(x ∈ [{a:.2f}, {current_b:.2f}])')
return polygon, integral_text
# 创建动画
ani = FuncAnimation(fig, update, frames=n_frames,
init_func=init, blit=True, interval=50, repeat=False)
plt.tight_layout()
plt.show()
# 如果要保存为gif(需要安装pillow):
# ani.save('integral_animation.gif', writer='pillow', fps=20)
这段代码的核心是:
- 用
Polygon创建可动态更新的填充区域 - 在
update()函数中逐步增加积分上限 - 用
np.trapz()计算数值积分值 - 实时显示当前积分区间和积分值
关键点:
Polygon.set_xy()动态更新多边形顶点np.trapz()进行梯形法数值积分FuncAnimation的blit=True提升动画性能
总结:用Polygon动态更新顶点实现积分面积填充。

