scipy.integrate.

nquad#

scipy.integrate.nquad(func, ranges, args=None, opts=None, full_output=False)[源代码]#

多变量积分。

封装了 quad 以实现多变量积分。各种选项允许改进不连续函数的积分,以及使用加权积分,并通常能更精细地控制积分过程。

参数:
func{可调用对象, scipy.LowLevelCallable}

要积分的函数。具有 x0, ... xn, t0, ... tm 等参数,其中积分在 x0, ... xn 上进行,它们必须是浮点数。其中 t0, ... tm 是在 args 中传递的额外参数。函数签名应为 func(x0, x1, ..., xn, t0, t1, ..., tm)。积分按顺序进行。也就是说,对 x0 的积分是最内层的积分,而对 xn 的积分是最外层的积分。

如果用户希望提高积分性能,则 f 可以是具有以下签名之一的 scipy.LowLevelCallable>:

double func(int n, double *xx)
double func(int n, double *xx, void *user_data)

其中 n 是变量和参数的数量。xx 数组包含坐标和额外参数。user_datascipy.LowLevelCallable 中包含的数据。

ranges可迭代对象

ranges 的每个元素可以是包含 2 个数字的序列,也可以是返回此类序列的可调用对象。ranges[0] 对应于在 x0 上的积分,依此类推。如果 ranges 的某个元素是可调用对象,则它将以所有可用的积分参数以及任何参数化参数进行调用。例如,如果 func = f(x0, x1, x2, t0, t1),则 ranges[0] 可以定义为 (a, b)(a, b) = range0(x1, x2, t0, t1)

args可迭代对象,可选

func, rangesopts 所需的附加参数 t0, ... tn

opts可迭代对象或字典,可选

要传递给 quad 的选项。可以是空的、字典,或字典序列,或返回字典的函数。如果为空,则使用 scipy.integrate.quad 的默认选项。如果是字典,则所有级别的积分都使用相同的选项。如果是序列,则序列的每个元素对应于特定的积分。例如,opts[0] 对应于在 x0 上的积分,依此类推。如果可调用,其签名必须与 ranges 相同。可用选项及其默认值如下:

  • epsabs = 1.49e-08

  • epsrel = 1.49e-08

  • limit = 50

  • points = None

  • weight = None

  • wvar = None

  • wopts = None

有关这些选项的更多信息,请参阅 quad

full_output布尔值,可选

scipy.integrate.quad 中 full_output 的部分实现。通过在调用 nquad 时设置 full_output=True,可以获得被积函数评估次数 neval

返回:
result浮点数

积分结果。

abserr浮点数

各种积分结果中绝对误差估计的最大值。

out_dict字典,可选

包含积分附加信息的字典。

另请参阅

quad

一维数值积分

dblquad, tplquad

二重和三重积分

fixed_quad

固定阶高斯积分

注释

为了获得有效结果,积分必须收敛;不保证发散积分的行为。

QUADPACK 级别例程的详细信息

nquad 调用 FORTRAN 库 QUADPACK 中的例程。本节详细说明了每个例程的调用条件以及每个例程的简要描述。调用的例程取决于 weightpoints 以及积分限 ab

QUADPACK 例程

权重

无限边界

qagse

None

No

No

qagie

None

No

Yes

qagpe

None

Yes

No

qawoe

‘sin’, ‘cos’

No

No

qawfe

‘sin’, ‘cos’

No

either a or b

qawse

‘alg*’

No

No

qawce

‘cauchy’

No

No

以下提供了 [1] 中每个例程的简短描述。

qagse

是一个基于全局自适应区间细分结合外推法的积分器,可消除多种类型的被积函数奇异性的影响。积分在每个子区间内使用 21 点 Gauss-Kronrod 积分法执行。

qagie

处理无限区间上的积分。无限区间被映射到有限区间,然后应用与 QAGS 相同的策略。

qagpe

与 QAGS 的用途相同,但还允许用户提供关于困难点(即内部奇异点、不连续点和被积函数其他困难处的横坐标)的位置和类型的明确信息。

qawoe

是一个积分器,用于在有限区间 [a,b] 上评估 \(\int^b_a \cos(\omega x)f(x)dx\)\(\int^b_a \sin(\omega x)f(x)dx\),其中 \(\omega\)\(f\) 由用户指定。规则评估组件基于修改后的 Clenshaw-Curtis 技术。

使用自适应细分方案结合外推过程,该过程是对 QAGS 中的修改,并允许算法处理 \(f(x)\) 中的奇异性。

qawfe

计算由用户提供的 \(\omega\)\(f\) 的傅里叶变换 \(\int^\infty_a \cos(\omega x)f(x)dx\)\(\int^\infty_a \sin(\omega x)f(x)dx\)QAWO 的过程应用于连续的有限区间,并通过 \(\varepsilon\) 算法对积分近似序列进行收敛加速。

qawse

近似计算 \(\int^b_a w(x)f(x)dx\),其中 \(a < b\),且 \(w(x) = (x-a)^{\alpha}(b-x)^{\beta}v(x)\),其中 \(\alpha,\beta > -1\),且 \(v(x)\) 可以是以下函数之一:\(1\), \(\log(x-a)\), \(\log(b-x)\), \(\log(x-a)\log(b-x)\)

用户指定 \(\alpha\)\(\beta\) 以及函数 \(v\) 的类型。应用全局自适应细分策略,并在包含 ab 的子区间上使用修改后的 Clenshaw-Curtis 积分。

qawce

计算 \(\int^b_a f(x) / (x-c)dx\),其中积分必须解释为柯西主值积分,用于用户指定的 \(c\)\(f\)。该策略是全局自适应的。在包含点 \(x = c\) 的区间上使用修改后的 Clenshaw-Curtis 积分。

参考文献

[1]

Piessens, Robert; de Doncker-Kapenga, Elise; Überhuber, Christoph W.; Kahaner, David (1983). QUADPACK: 自动积分子程序包。Springer-Verlag. ISBN 978-3-540-12553-2。

示例

计算

\[\int^{1}_{-0.15} \int^{0.8}_{0.13} \int^{1}_{-1} \int^{1}_{0} f(x_0, x_1, x_2, x_3) \,dx_0 \,dx_1 \,dx_2 \,dx_3 ,\]

其中

\[\begin{split}f(x_0, x_1, x_2, x_3) = \begin{cases} x_0^2+x_1 x_2-x_3^3+ \sin{x_0}+1 & (x_0-0.2 x_3-0.5-0.25 x_1 > 0) \\ x_0^2+x_1 x_2-x_3^3+ \sin{x_0}+0 & (x_0-0.2 x_3-0.5-0.25 x_1 \leq 0) \end{cases} .\end{split}\]
>>> import numpy as np
>>> from scipy import integrate
>>> func = lambda x0,x1,x2,x3 : x0**2 + x1*x2 - x3**3 + np.sin(x0) + (
...                                 1 if (x0-.2*x3-.5-.25*x1>0) else 0)
>>> def opts0(*args, **kwargs):
...     return {'points':[0.2*args[2] + 0.5 + 0.25*args[0]]}
>>> integrate.nquad(func, [[0,1], [-1,1], [.13,.8], [-.15,1]],
...                 opts=[opts0,{},{},{}], full_output=True)
(1.5267454070738633, 2.9437360001402324e-14, {'neval': 388962})

计算

\[\int^{t_0+t_1+1}_{t_0+t_1-1} \int^{x_2+t_0^2 t_1^3+1}_{x_2+t_0^2 t_1^3-1} \int^{t_0 x_1+t_1 x_2+1}_{t_0 x_1+t_1 x_2-1} f(x_0,x_1, x_2,t_0,t_1) \,dx_0 \,dx_1 \,dx_2,\]

其中

\[\begin{split}f(x_0, x_1, x_2, t_0, t_1) = \begin{cases} x_0 x_2^2 + \sin{x_1}+2 & (x_0+t_1 x_1-t_0 > 0) \\ x_0 x_2^2 +\sin{x_1}+1 & (x_0+t_1 x_1-t_0 \leq 0) \end{cases}\end{split}\]

\((t_0, t_1) = (0, 1)\)

>>> def func2(x0, x1, x2, t0, t1):
...     return x0*x2**2 + np.sin(x1) + 1 + (1 if x0+t1*x1-t0>0 else 0)
>>> def lim0(x1, x2, t0, t1):
...     return [t0*x1 + t1*x2 - 1, t0*x1 + t1*x2 + 1]
>>> def lim1(x2, t0, t1):
...     return [x2 + t0**2*t1**3 - 1, x2 + t0**2*t1**3 + 1]
>>> def lim2(t0, t1):
...     return [t0 + t1 - 1, t0 + t1 + 1]
>>> def opts0(x1, x2, t0, t1):
...     return {'points' : [t0 - t1*x1]}
>>> def opts1(x2, t0, t1):
...     return {}
>>> def opts2(t0, t1):
...     return {}
>>> integrate.nquad(func2, [lim0, lim1, lim2], args=(0,1),
...                 opts=[opts0, opts1, opts2])
(36.099919226771625, 1.8546948553373528e-07)