在python中动态构建lambda函数

use*_*761 6 python scipy

假设我想生成一个函数,稍后将其合并到一组方程中,用scipy nsolve函数求解.我想创建一个这样的函数:

xi + xi + 1 + xi + 3 = 1

其中变量的数量将取决于组件的数量.例如,如果我有2个组件:

 f = lambda x: x[0] + x[1] - 1
Run Code Online (Sandbox Code Playgroud)

为3:

 f = lambda x: x[0] + x[1] + x[2] - 1
Run Code Online (Sandbox Code Playgroud)

我将组件指定为要调用的函数的参数中的数组:

 def my_func(components):
        for component in components:
        .....
        .....
        return f
Run Code Online (Sandbox Code Playgroud)

我不能找到一种方法来做到这一点.我必须能够这样做,因为这个函数和其他函数需要与nsolve一起解决:

 x0 = scipy.optimize.fsolve(f, [0, 0, 0, 0 ....])
Run Code Online (Sandbox Code Playgroud)

任何帮助,将不胜感激

谢谢!


由于我不确定哪种方式最好,我将完全解释我要做的事情:

- 我正在尝试生成这两个函数,以便稍后解决:

在此输入图像描述

在此输入图像描述

所以我想创建一个函数teste([组件列表]),它可以返回这两个方程式(Psat(T)是一个我可以根据组件调用的函数,P是一个常量(值= 760)).

例:

  teste(['Benzene','Toluene'])
Run Code Online (Sandbox Code Playgroud)

会回来:

x苯:x甲苯= 1

xBenzene Psat ('Benzene')+ xToluene Psat('Toluene')= 760

在致电的情况下:

   teste(['Benzene','Toluene','Cumene'])
Run Code Online (Sandbox Code Playgroud)

它会返回:

x苯:x甲苯+ xCumene = 1

xBenzene Psat ('Benzene')+ xToluene Psat('Toluene')+ xCumene*Psat('Cumene')= 760

所有这些x值都不是我可以计算的东西,而是变成了我可以求和的列表.它们是根据我在系统中拥有的组件数量创建的变量...

希望这有助于找到这样做的最佳方式

Jon*_*nts 5

直接翻译是:

f = lambda *x: sum(x) - 1
Run Code Online (Sandbox Code Playgroud)

但不确定这是否真的是你想要的。


che*_*yos 5

您可以使用字符串动态构建lambda,然后使用eval函数进行解析,如下所示:

a = [1, 2, 3]

s = "lambda x: "
s += " + ".join(["x[" + str(i) + "]" for i in xrange(0, 3)]) # Specify any range
s += " - 1"

print s

f = eval(s)
print f(a)
Run Code Online (Sandbox Code Playgroud)

  • 仅当您从用户输入中获取字符串时, eval 才是危险的。显然,本申请中的情况并非如此。Jon 的答案假设 x 中的所有元素都必须求和,但情况可能并非如此。我只是展示一个如何动态创建足够灵活以服务 OP 的 lambda 的示例。 (3认同)

Jai*_*ime 2

我会利用 numpy 并做类似的事情:

\n\n
def teste(molecules):\n    P = np.array([Psat(molecule) for molecule in molecules])\n    f1 = lambda x: np.sum(x) - 1\n    f2 = lambda x: np.dot(x, P) - 760\n    return f1, f2\n
Run Code Online (Sandbox Code Playgroud)\n\n

实际上,您要解决的是一个可能欠定的线性方程组,其形式为 Ax = b。您可以按如下方式构造 A 和 b:

\n\n
A = np.vstack((np.ones((len(molecules),)),\n               [Psat(molecule) for molecule in molecules]))\nb = np.array([1, 760])\n
Run Code Online (Sandbox Code Playgroud)\n\n

然后您可以创建一个返回 2 元素向量的 lambda 函数,如下所示:

\n\n
return lambda x: np.dot(A, x) - b\n
Run Code Online (Sandbox Code Playgroud)\n\n

但我真的不认为这是解决方程的最佳方法:要么你有一个可以用 得到的解np.linalg.solve(A, b),要么你有一个具有无限多个解的线性系统,在这种情况下你想要找到的是解空间的基础,而不是该空间中的单个点,这是您将从以函数作为输入的数值求解器获得的结果。

\n