问题描述
我正在尝试优化一个模型,该模型涉及在共享变量的同时同时拟合数据的两个函数。由于 scipy.optimize 需要传递一个函数,我目前在最小化此模型时遇到问题,但我需要将两者一起最小化。
简化的代码块(在 symfit 中执行):
dictionary = ({y1: 3x**4 + 0.5y**3 + 2z**2 + w,y2: x*y * exp(z**2 - w)})
mixed_model = CallableNumericalModel(dictionary,connectivity_mapping = {y1:{x,y,z,w},y2:{x,w}})
model_sim = mixed_model(x=xdata,y=y,z=z,w=w)
res = minimize(mixed_model.ravel(),x0=2,args=(y,w),options={'eps':1e-3})
fit = Fit(res,x=xdata,y1=rhoxx_exp,y2=rhoxy_exp)
fit_result = fit.execute()
print(fit_result)
ValueError: `f0` passed has more than 1 dimension.
回溯表明此错误发生在行中:
res = minimize(mixed_model.ravel(),
正如我所说,这是因为我已经将模型传递给了最小化函数,而它必须是一个函数,但我不确定如何同时最小化 y1 和 y2 以适应它。
任何建议将不胜感激,在此先感谢您!
按照以下建议进行编辑,但具有实际功能:
def y1(B,n_1,n_2,n_3,n_4,mu_1,mu_2,mu_3,mu_4):
for i in range(len(dictionary)):
return (np.exp(B[i]/f)+np.exp(-B[i]/f))
return ( (rho1 / (rho1**2 + (R1*B)**2) + rho2 / (rho2**2 + (R2*B)**2)
+ rho3 / (rho3**2 + (R3*B)**2) + rho4 / (rho4**2 + (R4*B)**2))
/ ((rho1 / (rho1**2 + (R1*B)**2) + rho2 / (rho2**2 + (R2*B)**2)
+ rho3 / (rho3**2 + (R3*B)**2) + rho4 / (rho4**2 + (R4*B)**2))**2
+ ((-R1*B)/(rho1**2+(R1*B)**2) + (-R2*B)/(rho2**2+(R2*B)**2)
+ (-R3*B)/(rho3**2+(R3*B)**2) + (-R4*B)/(rho4**2+(R4*B)**2))**2)
+ (a/(np.exp(B/f)+np.exp(-B/f))/2)*((rho1 / (rho1**2 + (R1*B)**2) + rho2 / (rho2**2 + (R2*B)**2)
+ rho3 / (rho3**2 + (R3*B)**2) + rho4 / (rho4**2 + (R4*B)**2))
/ ((rho1 / (rho1**2 + (R1*B)**2) + rho2 / (rho2**2 + (R2*B)**2)
+ rho3 / (rho3**2 + (R3*B)**2) + rho4 / (rho4**2 + (R4*B)**2))**2
+ ((-R1*B)/(rho1**2+(R1*B)**2) + (-R2*B)/(rho2**2+(R2*B)**2)
+ (-R3*B)/(rho3**2+(R3*B)**2) + (-R4*B)/(rho4**2+(R4*B)**2))**2)) )
def y2(B,mu_4):
return ( - ((-R1*B)/(rho1**2+(R1*B)**2) + (-R2*B)/(rho2**2+(R2*B)**2)
+ (-R3*B)/(rho3**2+(R3*B)**2) + (-R4*B)/(rho4**2+(R4*B)**2)) /
((rho1 / (rho1**2 + (R1*B)**2) + rho2 / (rho2**2 + (R2*B)**2)
+ rho3 / (rho3**2 + (R3*B)**2) + rho4 / (rho4**2 + (R4*B)**2))**2
+ ((-R1*B)/(rho1**2+(R1*B)**2) + (-R2*B)/(rho2**2+(R2*B)**2)
+ (-R3*B)/(rho3**2+(R3*B)**2) + (-R4*B)/(rho4**2+(R4*B)**2))**2) )
def f(x0):
B,mu_4 = x0
error = []
expected_output = [(1,2),(3,4)]
for i in expected_output :
error += [y1(B,mu_4) - i[0],y2(B,mu_4) - i[1],]
return error
x0 = (0,1.51e27,-1.519e27,0.915e27,-1.047e27,1.41,0.64,0.087,0.09)
result = scipy.optimize.leastsq( f,x0,epsfcn = 1e-3)
IndexError: invalid index to scalar variable.
在函数 y1 中找到的指数线
任何进一步的建议都会令人惊讶,在此先感谢您!
解决方法
您必须要狡猾,但要使技巧最小化并没有那么难。关键是 minimize
仅适用于 scalar cost functions,但 leastsq
可以接受元组作为参数。所以,如果你能以某种方式使用 leastsq
来最小化你的函数。这种方法应该是这样的。
-
定义您希望最小化 y1(w,x,y,z),y2(w,...
的函数 -
将要最小化的函数定义为 f(),其中 x0 扩展为参数元组。
-
函数 f 返回离散测量样本与单个函数 y1、y2 等之间差异的向量。
-
让 SciPy 最小化这个函数,从合理选择的初始参数向量开始。
出于某种原因,我无法在 Stackoverflow 上正确设置格式。
这是关于 pastebin 的代码。