好吧那么我怎样才能使用curve_fit来编写一个代码来优化微分方程中的常数a和b,比如dy / dt = a * y ^ 2 + b?我将使用odeint来解决ODE,然后使用curve_fit来优化a和b。 如果你能提供关于这种情况的意见,我将非常感谢!
答案 0 :(得分:4)
通过查看ODEs with Sympy,您可能会得到更好的服务。 Scipy / Numpy基本上是数字包,并不是真正用来进行代数/符号操作。
答案 1 :(得分:4)
你绝对可以这样做:
import numpy as np
from scipy.integrate import odeint
from scipy.optimize import curve_fit
def f(y, t, a, b):
return a*y**2 + b
def y(t, a, b, y0):
"""
Solution to the ODE y'(t) = f(t,y,a,b) with initial condition y(0) = y0
"""
y = odeint(f, y0, t, args=(a, b))
return y.ravel()
# Some random data to fit
data_t = np.sort(np.random.rand(200) * 10)
data_y = data_t**2 + np.random.rand(200)*10
popt, cov = curve_fit(y, data_t, data_y, [-1.2, 0.1, 0])
a_opt, b_opt, y0_opt = popt
print("a = %g" % a_opt)
print("b = %g" % b_opt)
print("y0 = %g" % y0_opt)
import matplotlib.pyplot as plt
t = np.linspace(0, 10, 2000)
plt.plot(data_t, data_y, '.',
t, y(t, a_opt, b_opt, y0_opt), '-')
plt.gcf().set_size_inches(6, 4)
plt.savefig('out.png', dpi=96)
plt.show()
答案 2 :(得分:0)
为了解决这类问题,我决定编写一个统一sympy
和scipy
的包装程序包。它被称为symfit
。适合您的ODE将如下所示:
tdata = np.array([10, 26, 44, 70, 120])
ydata = 10e-4 * np.array([44, 34, 27, 20, 14])
y, t = variables('y, t')
a, b = parameters('a, b')
model_dict = {
D(y, t): a*y^2 + b
}
ode_model = ODEModel(model_dict, initial={t: 0.0, y: 0.0})
fit = Fit(ode_model, t=tdata, y=ydata)
fit_result = fit.execute()
从它被定义为dict的方式可以看出,适合(一阶)ODE系统是没有问题的。查看docs了解更多信息!