我想使用scipy.integrate.quad来评估函数的积分。以下是被积函数的样子: 我们可以注意到,该被积函数的大部分贡献将来自.1到4或5。对于x = 10或更大,虽然函数是振荡的(很难在图片上看出来),但它非常小并且不断变小。
以下是从0到某些上限的整合结果。积分的上限在x轴上。 在这里,虽然结果似乎在前100个x中是稳定的,但不久之后,即使我期待一条直线......
我对python很新,我不知道什么是最好的行动方案。我现在最好的猜测是将一些小于100的值作为积分的上限,并丢弃其他值,因为它只是来自integrate.quad的一个不好的收敛。
修改 为了绘制第二个图,我使用了scipy.integrate.quad函数。但是,如果我只是采用我生成的点来绘制被积函数(第一个数字)并在scipy.integrate.simps中使用它并改变我整合的最大x,我得到一致的结果。
答案 0 :(得分:5)
当被积函数具有远小于积分范围的重要特征时,它可能会被忽略"通过自适应quad
例程。相反,simps
如果使用足够精细的网格,则不会错过它们,但可能需要更长时间才能进行评估。我将介绍两种解决方法,第二种方法更实用。
您可以使用points
的{{1}}参数来确保不会发生这种情况。这是一个例子,我在区间[-1000,5000]上集成了高斯函数quad
。该函数位于0附近;几乎所有这些都在区间[-5,5]中,所以我包括exp(-x**2)
以确保不会忽略这个范围。 (这些点必须在整合范围内,因此出现points=[-5, 5]
)。
if
红色曲线是没有import numpy as np
from scipy.integrate import quad
import matplotlib.pyplot as plt
f = lambda x: np.exp(-x**2)
numpoints = 1000
t = np.linspace(-1000, 5000, numpoints)
y = np.zeros((numpoints,))
for i in range(numpoints):
y[i] = quad(f, -1000, t[i])[0] # integration without points
plt.plot(t, y, 'r')
for i in range(numpoints): # using points if upper bound is above 5
y[i] = quad(f, -1000, t[i], points=[-5,5])[0] if t[i] > 5 else quad(f, -1000, t[i])[0]
plt.plot(t, y, 'b')
plt.show()
的输出,蓝色曲线是points
。后者的行为应该如此:从0上升到pi / 2并保持在那里。
在多个点计算反衍生物的更有效的方法是使用先前计算的值,向其添加未积分的区间的贡献。
points
这与上面的蓝色曲线具有相同的输出。