以变量作为积分限制的积分(python)

以变量作为积分限制的积分(python),python,scipy,quad,Python,Scipy,Quad,我需要与python进行集成,但其中一个限制是变量,而不是数字(从0到z) 我尝试了以下方法: import numpy as np import matplotlib.pyplot as plt from scipy.integrate import quad def I(z,y,a): #function I want to integrate I = (a*(y*(1+z)**3+(1-y))**(0.5))**(-1)

我需要与python进行集成,但其中一个限制是变量,而不是数字(从0到z)

我尝试了以下方法:

    import numpy as np
    import matplotlib.pyplot as plt
    from scipy.integrate import quad

    def  I(z,y,a):    #function I want to integrate

      I = (a*(y*(1+z)**3+(1-y))**(0.5))**(-1)

      return I

    def dl(z,y,a):  #Integration of I

      dl = quad(I, 0, z, args =(z,y,a))

      return dl
我遇到的问题是,
dl(z,y,a)
给了我一个数组,所以每当我想要绘制或计算它时,我都会得到以下结果:

    import numpy as np
    import matplotlib.pyplot as plt
    from scipy.integrate import quad

    def  I(z,y,a):    #function I want to integrate

      I = (a*(y*(1+z)**3+(1-y))**(0.5))**(-1)

      return I

    def dl(z,y,a):  #Integration of I

      dl = quad(I, 0, z, args =(z,y,a))

      return dl
ValueError:包含多个元素的数组的真值不明确


我不知道是否有任何解决方案。感谢高级我认为
quad
不接受向量值积分边界。因此,在这种情况下,您实际上必须循环使用
z
或使用
np.vectorize
编辑:在代码中,您应该只使用
args
参数作为
agrs=(y,a)
,而不应该包括z。然后,您可以通过索引返回元组的第一个元素来访问集成结果

实际上,
quad
返回一个元组。元组中的第一个元素是所需的reuslt。因为我不能让你的代码毫无问题地运行,所以我写了一些简短的代码。我不确定这是否是您想要的:

def I(a):
    return lambda z, y: (a*(y*(1+z)**3+(1-y))**(0.5))**(-1)

def dl(z, y, a):
    return quad(I(a), 0, z, args=(y))

print(dl(1,2,3)[0])
结果:

0.15826362868629346

Python需要考虑的是,将空列表(或iterable)强制转换为布尔值时为false。想象你正在列出一些东西

当你在做计算时,你可以考虑零向量,[0,0,0],在线性AlgBRA中可以被认为是零,但不是空列表。 您的错误似乎来自非空检查。


正如其他答案所表明的那样,您错误地计算了一个函数,并提供了一个预期数字所在的数组。

使用
I
调用
quad
的正确方法是:

In [20]: quad(I, 0, 10, args=(1,2))
Out[20]: (0.6984886554222364, 1.1361829471531105e-11)
正如龙文所指出的,
I
的第一个参数是
z
,它的
quad
有所不同。
(y,a)
quad
传递给
I
的参数,不作更改

但是您得到了错误,因为您尝试使用数组作为
z
边界

In [21]: quad(I, 0, np.arange(3), args=(1,2))
---------------------------------------------------------------------------
ValueError                                Traceback (most recent call last)
<ipython-input-21-fbbfa9c0cd3f> in <module>()
----> 1 quad(I, 0, np.arange(3), args=(1,2))

/usr/local/lib/python3.5/dist-packages/scipy/integrate/quadpack.py in quad(func, a, b, args, full_output, epsabs, epsrel, limit, points, weight, wvar, wopts, maxp1, limlst)
    313     if (weight is None):
    314         retval = _quad(func, a, b, args, full_output, epsabs, epsrel, limit,
--> 315                        points)
    316     else:
    317         retval = _quad_weight(func, a, b, args, full_output, epsabs, epsrel,

/usr/local/lib/python3.5/dist-packages/scipy/integrate/quadpack.py in _quad(func, a, b, args, full_output, epsabs, epsrel, limit, points)
    362 def _quad(func,a,b,args,full_output,epsabs,epsrel,limit,points):
    363     infbounds = 0
--> 364     if (b != Inf and a != -Inf):
    365         pass   # standard integration
    366     elif (b == Inf and a != -Inf):

ValueError: The truth value of an array with more than one element is ambiguous. Use a.any() or a.all()

你是在积分变量y还是z?您正在集成的函数也包含z,如果您可以包含一个使用示例,可能会比较容易混淆。是的,你是对的,函数也包含z,也许这是问题之一,谢谢。是的,我想这就是我需要的,我真的不明白为什么你不把变量“a”放在args()中。无论如何,非常感谢你@Brny
args
应包含除您正在对其进行积分的参数之外的参数。在我的例子中,函数I(a)实际返回的函数包含两个参数y和z。当我把它传递给
quad
函数时,它实际上只接受一个额外的参数(y),除了我正在积分的变量(z)。这就是为什么我只在
args
中包含y。但它和你的密码一样好的,我知道了。谢谢