【发布时间】:2016-04-21 15:18:47
【问题描述】:
我对使用 python 进行数据分析以及使用 lmfit 进行非线性方程拟合有些陌生。我正在尝试模拟一个复杂的半解析函数,该函数描述污染物羽流在 1D 通道中随时间的运动。我正在使用 lmfit v0.9.3。我已经成功完成了 lmfit 教程中的几个示例,但似乎无法让我自己的模型正常工作。下面的脚本在 tsm_mod.fit() 调用之前有效,但随后返回错误:
文件“C:\Anaconda\lib\site-packages\lmfit\model.py”,第 501 行,在 合身 对于 p in params.values()])
TypeError: 'numpy.ndarray' 对象不可调用
代码如下:
import numpy as np
import scipy as sp
import pandas as pd
from lmfit import Model
desmedt = pd.read_table('Directory\desmedt_test.txt',sep='\t')
x = desmedt['Times']
y = desmedt['Conc']
def tsm_intfunc(t,x,tau,u,k,alpha,beta,mass,ac):
return((mass/(2*ac*(t*np.pi*k)**(1/2)))*np.exp(-((x-u*t)**2)/(4*k*t))*np.exp(-alpha*tau-alpha*(t-tau)/beta)
*np.sqrt(beta*tau/(t-tau))*sp.special.iv(2*np.sqrt((alpha**2)*tau*(t-tau)/beta),1))
def tsm_desmedt(t,x,u,k,alpha,beta,mass,ac,nsteps):
dtau = t/nsteps
cxt = (mass/(2*ac*np.sqrt(t*np.pi*k)))*np.exp(-((x-u*t)**2)/(4*k*t))*np.exp(-alpha*t)
cxv = tsm_intfunc(t,x,0.00000001,u,k,alpha,beta,mass,ac)/2
i = 1
while (i<nsteps):
cxv = cxv+tsm_intfunc(t,x,dtau*i,u,k,alpha,beta,mass,ac)/2
i = i+1
return cxt+(alpha/beta)*cxv*dtau
tsm_mod = Model(tsm_desmedt)
tsm_mod.set_param_hint('ac',value=18.2,vary=False)
tsm_mod.set_param_hint('alpha',value=1e-4)
tsm_mod.set_param_hint('beta',value=1e-1)
tsm_mod.set_param_hint('k',value=3)
tsm_mod.set_param_hint('mass',value=157100,vary=False)
tsm_mod.set_param_hint('nsteps',value=100,vary=False)
tsm_mod.set_param_hint('u',value=0.4)
tsm_mod.set_param_hint('x',value=4604,vary=False)
tsm_pars = tsm_mod.make_params()
tsm_fit = tsm_mod.fit(y,x,tsm_pars)
这可能是 lmfit 中的错误吗?或者,您认为我使用 lmfit 设置问题的方式有误吗?
编辑: 拟合中用到的数据如下:
次
7787.628 8330.04 8640 8756.244 8988.696 9143.676 9337.392 9492.372 9724.86 9918.576 10034.784 10228.536 10383.516 10577.232 10770.948 11003.4 11119.644 11313.36 11468.34 11700.792 11855.772 12010.752 12204.468 12359.448 12630.672 12824.388 13173.084 13483.044 13793.004 14412.924 14955.336 15575.256 16195.14 17357.472
浓度
0.00944669 0.0850202 0.236167 0.576248 1.00135 2.01215 2.84345 3.51417 4.53441 5.21457 5.59244 5.74359 5.88529 6.0081 5.75304 5.61134 5.20513 4.95007 4.41161 3.74089 3.46694 3.07962 2.80567 2.41835 2.1444 1.74764 1.47368 1.20918 0.935223 0.661269 0.406208 0.132254 0.11336 0.151147
【问题讨论】:
-
您能否提供您正在使用的数据或至少其中的一部分?
-
根据docs online,
Model.fit期望被传递的args数据,params,weights,...;你给了它 y, x, tsm_pars,这对我来说显然不正确。特别是,它将把你的x当作它的params,它期望它是一个Parameters对象。 -
按照我在网上看到的——我自己从来没有使用过 py-lmfit——我想你可能想要
tsm_fit = tsm_mod.fit(y, tsm_pars, x=x)这样的东西。 -
我已编辑问题以包含拟合中使用的数据。这是从 desmedt 文本文件中导入的数据。另外,我相信我让它工作了:我没有意识到 Gareth 建议的格式需要一个指向函数参数列表中自变量的指针,因为它写在参数中: tsm_fit=tsm_mod.fit(y, tsm_pars , t=x) 谢谢大家的及时回复。