You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用Python symfit ODEModel拟合多维数据遇参数传递错误求助

问题:symfit ODEModel拟合多维数据时出现TypeError错误

尝试用symfit的ODEModel拟合含时变输入的ODE参数,参考官方《Fitting multidimensional datasets》示例编写代码,但运行时出现TypeError: got an unexpected keyword argument 'inp'错误。

原实现代码

import symfit as sf 
import numpy as np

# data 
x = np.arange(0,19) 
data = 10e-4 * np.array([8,10,12,11,10,15,25,37,46,40,43,35,27,14,8,10,13,9,10]) 
data2 = 10e-3 * np.array([0,0,0,0,0,1,1,1,1,1,1,1,1,1,0,0,0,0,0]) 

# model 
t, mp, inp = sf.variables('t, mp, inp') 
tau, w = sf.parameters('tau, w') 
model = {sf.D(mp, t): (-mp + inp * w) / tau } 

# fitting 
ode_model = sf.ODEModel(model, initial={inp: data2[0], t: 0.0, mp: data[0]})
fit = sf.Fit(ode_model, inp=data2, t=x, mp=data) 
fit_result = fit.execute() 

完整错误栈

/usr/local/lib/python3.10/dist-packages/symfit/core/fit.py in __init__(self, model, objective, minimizer, constraints, absolute_sigma, *ordered_data, **named_data)
    372         # Bind as much as possible the provided arguments.
    373         signature = self._make_signature()
--> 374         bound_arguments = signature.bind_partial(*ordered_data, **named_data)
    375 
    376         # Select objective function to use. Has to be done before calling

/usr/lib/python3.10/inspect.py in bind_partial(self, *args, **kwargs)
   3191         Raises `TypeError` if the passed arguments can not be bound.
   3192         """
-> 3193         return self._bind(args, kwargs, partial=True)
   3194 
   3195     def __reduce__(self):

/usr/lib/python3.10/inspect.py in _bind(self, args, kwargs, partial)
   3173                 arguments[kwargs_param.name] = kwargs
   3174             else:
-> 3175                 raise TypeError(
   3176                     'got an unexpected keyword argument {arg!r}'.format(
   3177                         arg=next(iter(kwargs))))

TypeError: got an unexpected keyword argument 'inp'

错误原因

你的怀疑正确:inp不是模型的自变量,而是随时间变化的输入信号。原代码中错误地将inp作为独立变量定义,并且在sf.Fit()中当作输入参数传入,导致symfit无法识别该参数。

修正方案

将inp定义为时间t的函数,而非独立变量,同时调整初始条件和拟合参数的传入方式:

修正后的代码

import symfit as sf 
import numpy as np

# 数据
x = np.arange(0,19) 
data = 10e-4 * np.array([8,10,12,11,10,15,25,37,46,40,43,35,27,14,8,10,13,9,10]) 
data2 = 10e-3 * np.array([0,0,0,0,0,1,1,1,1,1,1,1,1,1,0,0,0,0,0]) 

# 模型定义:将inp声明为t的函数
t, mp = sf.variables('t, mp') 
tau, w = sf.parameters('tau, w')
inp = sf.Function('inp')(t)  # 将inp定义为t的函数
model = {sf.D(mp, t): (-mp + inp * w) / tau } 

# 创建ODEModel:仅需设置状态变量mp的初始条件和初始时间,无需设置inp的初始值
ode_model = sf.ODEModel(model, initial={t: 0.0, mp: data[0]})

# 拟合:将inp的观测数据与t对应传入
fit = sf.Fit(ode_model, t=x, inp=data2, mp=data) 
fit_result = fit.execute()

# 打印拟合结果
print(fit_result)

关键修正点

  1. 定义inp为t的函数:用sf.Function('inp')(t)将inp声明为随时间变化的输入,而非独立变量,让symfit识别其为时变输入信号。
  2. 调整初始条件:初始条件只需设置状态变量mp和初始时间t,inp是输入信号无需设置初始值。
  3. 正确传入拟合数据:在sf.Fit()中通过inp=data2将输入数据与时间t=x绑定,模型会在每个时间点使用对应的inp值进行积分计算。

内容的提问来源于stack exchange,提问作者soupinacanoe

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.18 11:57:21