在使用fsolve()进行求解之前,将渐近表达式转换为数值表达式 [英] Converting sympy expression to numpy expression before solving with fsolve( )
本文介绍了在使用fsolve()进行求解之前,将渐近表达式转换为数值表达式的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!
问题描述
我有一个用渐近度表示的方程系统:
def test1a(A):
t, tt = sym.symbols('t tt')
return sym.cos(t+tt+A)*A
def test1b(B):
t, tt = sym.symbols('t tt')
return sym.sin(t-tt+B)*B
我想在使用fsolve()
计算结果之前将其转换为数值表达式:
def testprep(variables, A, B):
t, tt = sym.symbols('t tt')
fA = lambdify([(t, tt)], test1a(A))
fB = lambdify([(t, tt)], test1b(B))
t, tt = variables
return [fA,fB]
def testsolve(A, B):
print(so.fsolve(testprep, [-1, 1], args = (A, B)))
return
运行时,我得到以下结果:
import scipy.optimize as so
import sympy as sym
from sympy.utilities.lambdify import lambdify as lambdify
import numpy as np
def main():
A = 1
B = 2
testsolve(A,B)
return
if __name__ == '__main__':
main()
输出:
error: Result from function call is not a proper array of floats.
作为一种理智的检查,我在麻木表情方面起草了同样的系统,并解决了它:
def standard(variables, A, B):
t, tt = variables
eq1 = np.cos(t+tt+A)*A
eq2 = np.sin(t-tt+B)*B
return [eq1, eq2]
def solvestandard(A, B):
print(so.fsolve(standard, np.array([-1, 1]), args = (A,B)))
return
输出:
[-0.71460184 1.28539816]
我是lambdify( )
的新手,不太熟悉从有症状到麻木的转换过程。我需要进行哪些更改才能使测试用例正常工作?
推荐答案
对于SO问题,您以一种非常复杂的方式呈现了代码。您不需要这么多函数来显示基本上只有5行代码!
请将您的示例简化为尽可能简单的内容,即可以复制粘贴完成所有导入的单个代码块。然后,请通过复制粘贴并在新的python进程中运行来测试它。
将lambdify
与fsolve
一起使用的方法如下:
import sympy as sym
import scipy.optimize as so
t, tt = sym.symbols('t tt')
A, B = 1, 2
eq1 = sym.cos(t+tt+A)*A
eq2 = sym.sin(t-tt+B)*B
f = lambdify([(t, tt)], [eq1, eq2])
print(so.fsolve(f, [-1, 1]))
这个想法是,lambdify创建了一个可以多次计算的高效函数(例如,fsolve
将迭代调用它)。然后将该高效函数传递给fsolve
。
传递给fsolve
的函数不应调用lambdify
本身(就像您的testprep
那样),因为lambdify
比计算函数慢得多:
In [22]: %time f = lambdify([(t, tt)], [eq1, eq2])
CPU times: user 4.74 ms, sys: 77 µs, total: 4.82 ms
Wall time: 4.96 ms
In [23]: %time f([1, 2])
CPU times: user 36 µs, sys: 1e+03 ns, total: 37 µs
Wall time: 41 µs
Out[23]: [-0.6536436208636119, 1.682941969615793]
也许您的实际问题更复杂,但我会使用希蒙尼的nsolve
来解决这样的问题:
In [16]: nsolve([eq1, eq2], [t, tt], [-1, 1])
Out[16]:
⎡-0.714601836602552⎤
⎢ ⎥
⎣ 1.28539816339745 ⎦
In [17]: nsolve([eq1, eq2], [t, tt], [-1, 1], prec=100)
Out[17]:
⎡-0.714601836602551690384339154180124278950707650156223544756263851923045898428447750342991293664470733⎤
⎢ ⎥
⎣1.285398163397448309615660845819875721049292349843776455243736148076954101571552249657008706335529267 ⎦
SymPy的nsolve
负责为您调用lambdify
。它比fsolve
慢一些,因为它可以处理任意精度的浮点数,但这意味着它也可以计算出更准确的结果。
这篇关于在使用fsolve()进行求解之前,将渐近表达式转换为数值表达式的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!
查看全文