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)给了我一个数组,所以每当我想绘制或评估它时,我都会获得以下信息:

ValueError:具有多个元素的数组的真值不明确。

我不知道是否有任何解决方案。在此先感谢

4

4 回答 4

1

编辑:在您的代码中,您应该只包含您的args参数 as agrs=(y, a), z 。然后,您可以通过索引返回元组的第一个元素来访问积分结果。

实际上quad返回一个元组。元组中的第一个元素是你想要的结果。由于我无法让您的代码毫无问题地运行,因此我编写了一些短代码。我不确定这是否是您想要的:

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
于 2017-02-23T15:18:51.103 回答
1

The correct way to call quad with your I is:

In [20]: quad(I, 0, 10, args=(1,2))
Out[20]: (0.6984886554222364, 1.1361829471531105e-11)

As Longwen points out, the first argument to I is the z that quad varies. The (y,a) are parameters that quad passes on to I without change.

But you got the error because you tried using an array as the z boundary

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()

ValueError when using if commands in function - another recent question trying to do the same thing, use an array as an integration boundary. That post gave more of the error traceback, so it was easier to identify the problem.


If it hadn't been for this ValueError, your 3 term args would have produced a different error:

In [19]: quad(I, 0, 10, args=(10,1,2))
....
TypeError: I() takes 3 positional arguments but 4 were given
于 2017-02-23T17:17:01.657 回答
0

我不认为quad接受向量值积分边界。因此,在这种情况下,您实际上必须循环z或使用np.vectorize.

于 2017-02-23T14:43:59.777 回答
0

Python 的考虑是空列表(或可迭代)在转换为布尔值时为假。想象一下你正在列出一些东西。

在进行计算时,您可以考虑零向量 [0,0,0] 在线性代数中可能被视为零但不是空列表。

You error seems to come from an not null checking. As other answers suggest you miscalled a function and provided an array where a number was expected.

于 2017-02-23T15:33:18.390 回答