【问题标题】:Integration using Lambda function gives an error使用 Lambda 函数集成会出错
【发布时间】:2021-07-22 22:01:33
【问题描述】:

我第一次尝试使用 Lambda 函数集成指数函数。 有两个版本的代码应该可以正常工作,但是带有 Lambda 函数的代码会给出错误提示:

给出错误的代码是

import numpy as np
import sympy as sym

# Predetermined parameter values 
s, t, T= 0.2 ,0, 0.25
a1, a2= 1.2, 2.3
X1, X2, X3=0.5,-2.0,0.3
# Symbolic variable for integration
u = sym.symbols('u')

# Version 1 giving the above error
fx= lambda X1,X2,X3,a1,a2,T,u: (X1*sym.exp(-a1*(T-u)) + X2*sym.exp(-a2*(T-u))+X3)**2             
Fx=sym.integrate(sym.expand(fx), (u,t,s))
Fx=float(Fx)

另一方面,我可以在没有 Lambda 函数的情况下使用以下版本获得输出 Fx。

# Version 2 works fine
def expFun3fsq(X1,X2,X3,a1,a2,T,u):
    # Squared single line exponential function 
    # It returns a symbolic function where u is the only symbol in the function
    fx= (X1*sym.exp(-a1*(T-u))+X2*sym.exp(-a2*(T-u))+X3) **2
    return fx

Fx=sym.integrate(sym.expand(expFun3fsq(X1,X2,X3,a1,a2,T,u)), (u,t,s))
Fx=float(Fx)

错误的原因是什么,我该如何解决?

【问题讨论】:

    标签: integration sympy lambda-calculus


    【解决方案1】:

    当您编写f = lambda x: 1 + x 时,您是在告诉python 您将为f 提供一个参数(如f(1)),并且该参数应在公式中引用为x。如果您希望能够轻松更改表达式的参数,则只需要一个 lambda(在我的示例中,f 将为您传递给它的任何内容添加 1)。

    当您编写 f = lambda: 1 + x 时,这意味着您不会传递任何参数,而您只希望函数使用 x 的本地值并加 1。

    >>> f = lambda: x + 1
    >>> g = lambda x: x + 1
    >>> x = 1
    >>> f()
    2
    >>> g(1)
    2
    >>> x = 3
    >>> f()
    4
    >>> g(1)
    2    
    

    确保您理解上述输出很重要。 lambda 的行为方式与已定义函数的行为相同——并且您表明您知道如何使用已定义函数。

    由于您修复了除u 之外的所有内容,并且您想要集成一个作为u 函数的表达式,您必须以某种方式定义该表达式:您可以将参数传递给一个函数/ lambda(正确)来获取该表达式或只编写表达式。所以将fx= lambda X1,X2,X3,a1,a2,T,u: 更改为fx = ,你的代码就可以工作了。或者,像使用函数一样将所有变量传递给 lambda。

    >>> s, t, T= 0.2 ,0, 0.25
    >>> a1, a2= 1.2, 2.3
    >>> X1, X2, X3=0.5,-2.0,0.3
    >>> u = sym.symbols('u')
    

    这里,fx 是表达式

    >>> fx=  (X1*sym.exp(-a1*(T-u)) + X2*sym.exp(-a2*(T-u))+X3)**2
    >>> fx.subs(u, 0)  # less convenient than using a lambda as shown last below
    0.207025570818871
    >>> Fx1=sym.integrate(sym.expand(fx), (u,t,s))
    

    这里,fx 是我们必须向其传递所有参数的函数

    >>> fx = lambda X1,X2,X3,a1,a2,T,u:(X1*sym.exp(-a1*(T-u)) + X2*sym.exp(-a2*(T-u))+X3)**2             
    >>> Fx2=sym.integrate(sym.expand(fx(X1,X2,X3,a1,a2,T,u)), (u,t,s))
    

    这里,fxu 的函数,我们使用变量的局部值

    >>> fx = lambda u:(X1*sym.exp(-a1*(T-u)) + X2*sym.exp(-a2*(T-u))+X3)**2     
    >>> fx(0)
    0.207025570818871   
    >>> fx(u).n(2)
    1.3*(0.33*exp(1.2*u) - exp(2.3*u) + 0.27)**2
    >>> Fx3=sym.integrate(sym.expand(fx(u)), (u,t,s))
    

    所有方法都给出相同的答案:

    >>> Fx1,Fx2, Fx3
    (0.106060402899230, 0.106060402899230, 0.106060402899230)
    

    【讨论】:

    • 您好@smichr 非常感谢您的详细解释。请问fx(u).n(2)在上面的第三个版本(使用变量的局部值)中是做什么的?我在 n(x) 中的数字附近玩过,它似乎是一个显示选项?
    • 即把表达式(或表达式,当为数值表达式时)中的数字求值到给定的位数。你也可以通过help(fx(u).n)获得帮助。
    • 好的,谢谢!感谢您的详细解释和示例,我现在对 Lambda 函数的使用有了更好的理解 :)
    猜你喜欢
    • 2019-02-21
    • 1970-01-01
    • 2019-12-03
    • 2020-10-26
    • 2020-08-22
    • 2021-09-17
    • 1970-01-01
    • 1970-01-01
    • 2021-06-28
    相关资源
    最近更新 更多