Python 同时优化两个不同的函数,为两者提供通用的解决方案

Python 同时优化两个不同的函数,为两者提供通用的解决方案,python,scipy,scipy-optimize,symfit,Python,Scipy,Scipy Optimize,Symfit,我在一月份问了一个类似的问题,@Miłosz Wieczór很乐意回答。现在,我面临着一个类似但不同的挑战,因为我需要在两个数据集(e_exp和iq_exp)上同时拟合两个参数(fc和alpha)。我基本上需要找到最适合数据e_exp和iq_exp的fc和alpha值 import numpy as np import math from scipy.optimize import curve_fit, least_squares, minimize f_exp = np.array([1,

我在一月份问了一个类似的问题,@Miłosz Wieczór很乐意回答。现在,我面临着一个类似但不同的挑战,因为我需要在两个数据集(
e_exp
iq_exp
)上同时拟合两个参数(
fc
alpha
)。我基本上需要找到最适合数据
e_exp
iq_exp
fc
alpha

import numpy as np
import math
from scipy.optimize import curve_fit, least_squares, minimize

f_exp  = np.array([1, 1.6, 2.7, 4.4, 7.3, 12, 20, 32, 56, 88, 144, 250000])
e_exp  = np.array([7.15, 7.30, 7.20, 7.25, 7.26, 7.28, 7.32, 7.25, 7.35, 7.34, 7.37, 11.55])
iq_exp = np.array([0.010, 0.009, 0.011, 0.011, 0.010, 0.012, 0.019, 0.027, 0.038, 0.044, 0.052, 0.005])

ezero  = np.min(e_exp)
einf   = np.max(e_exp)

ig_fc     = 500
ig_alpha  = 0.35

def CCRI(f_exp, fc, alpha):
    x   = np.log(f_exp/fc)
    R  = ezero + 1/2 * (einf - ezero) * (1 + np.sinh((1 - alpha) * x) / (np.cosh((1 - alpha) * x) + np.sin(1/2 * alpha * math.pi)))
    I  = 1/2 * (einf - ezero) * np.cos(alpha * math.pi / 2) / (np.cosh((1 - alpha) * x) + np.sin(alpha * math.pi / 2))
    RI = np.sqrt(R ** 2 + I ** 2)
    return RI

def CCiQ(f_exp, fc, alpha):
    x   = np.log(f_exp/fc)
    R  = ezero + 1/2 * (einf - ezero) * (1 + np.sinh((1 - alpha) * x) / (np.cosh((1 - alpha) * x) + np.sin(1/2 * alpha * math.pi)))
    I  = 1/2 * (einf - ezero) * np.cos(alpha * math.pi / 2) / (np.cosh((1 - alpha) * x) + np.sin(alpha * math.pi / 2))
    iQ = I / R
    return iQ

poptRI, pcovRI = curve_fit(CCRI, f_exp, e_exp, p0=(ig_fc, ig_alpha))

poptiQ, pcoviQ = curve_fit(CCiQ, f_exp, iq_exp, p0=(ig_fc, ig_alpha))
einf
ezero
f_exp
都是常量,另外我需要优化的变量是
ig_fc
ig_alpha
,其中
ig
代表初始猜测。在上面的代码中,我得到了两个不同的
fc
alpha
值,因为我独立求解它们。然而,我需要同时解决它们,以便
fc
alpha
是通用的

  • 有没有办法解决两个不同的函数,为
    fc
    alpha
    提供通用解决方案

文档在第二个返回值上的状态来自:

pcov

popt的估计协方差。对角线提供参数估计的方差。计算一个标准差 参数错误使用
perr=np.sqrt(np.diag(pcov))

因此,如果你想最小化整体误差,你需要将两种拟合的误差结合起来

def objective(what, ever):

    poptRI, pcovRI = curve_fit(CCRI, f_exp, e_exp, p0=(ig_fc, ig_alpha))

    poptiQ, pcoviQ = curve_fit(CCiQ, f_exp, iq_exp, p0=(ig_fc, ig_alpha))

    # not sure if this the correct equation, but you can start with it
    err_total = np.sum(np.sqrt(np.diag(pcovRI))) + np.sum(np.sqrt(np.diag(pcoviQ)))

    return err_total
关于二维高斯函数的总误差:

更新: 由于您希望
poptRI
poptiQ
相同,因此需要最小化它们之间的距离

可以这样做

from numpy import linalg

def objective(what, ever):

    poptRI, pcovRI = curve_fit(CCRI, f_exp, e_exp, p0=(ig_fc, ig_alpha))

    poptiQ, pcoviQ = curve_fit(CCiQ, f_exp, iq_exp, p0=(ig_fc, ig_alpha))

    delta = linalg.norm(poptiQ - poptRI)
    return delta
最小化此函数将(应该)导致
poptRI
poptiQ
的值相似。将参数作为向量,并尝试最小化其增量向量的长度

但是,这种方法假设
poptRI
poptiQ
(及其系数)在相同的范围内,因为您对它们使用了一些度量。如果说其中一个在2000范围内,另一个在2范围内。然后优化器将倾向于调整第一个。但也许这很好

如果你想以同样的方式对待他们,你需要使他们正常化。 一种方法(假设所有系数相似)可以是

将结果规格化为单位向量,然后减去它们,然后创建范数

对于函数的输入也是如此,但它可能没有那么重要。请参阅下面的链接

但这在很大程度上取决于您试图解决的问题。没有普遍的解决办法

与此相关的一些链接:

另一个目标函数:

这就是你想做的吗? 您希望找到最佳的
fc
alpha
,以便两个函数的拟合结果尽可能接近

def objective(fc, alpha):

    poptRI, pcovRI = curve_fit(CCRI, f_exp, e_exp, p0=(fc, alpha))

    poptiQ, pcoviQ = curve_fit(CCiQ, f_exp, iq_exp, p0=(fc, alpha))

    delta = linalg.norm(poptiQ - poptRI)
    return delta

创建一个目标函数,使用曲线拟合的两个结果??感谢您的评论和提供链接,@Joe。我仍然不确定如何将两者结合成一个目标函数。“你能详细说明一下吗?再次谢谢你,”乔说。实际上,我想找到
fc
alpha
的最佳估计值,我猜当误差为最低可能值时,会出现这种情况。因此,我不需要组合
pcovRI
pcoviQ
,而是需要找到包含
poptRI
poptiQ
的公共值。你对如何组合它们有什么想法吗?请参阅第二个反对函数。谢谢你,@Joe。你可能比我领先两步(如果不是更多的话)。如果独立运行它们,
poptRI[0]=2549.59
poptRI[1]=0.2921
poptiQ[0]=2801.64
poptiQ[1]=0.3202
,其中
[0]=fc
[1]=alpha
。如果我用
what=e_exp
ever=iq_exp
运行你的目标函数,delta返回
252.04
,我希望它介于
poptRI[0]
poptiQ[0]
之间。我还需要
alpha
poptRI[1]
poptiQ[1]
)但没有提供。我试图简单地添加并返回
delta2=linalg.norm(poptiQ[1]-poptRI[1])
,但这个值也太小了。我为我的无知道歉。我没有完全理解你想做什么。您可能需要向目标函数添加更多自由变量,如
def objective(您需要什么)
。可能是
alpha
fc
?我还添加了一些关于标准化的内容。因此,由于
CCRI
中的
fc
alpha
poptRI[0]
poptRI[1]
)与
CCiQ
中的相同参数不同(
poptiQ[0]
poptiQ[1]
),我想同时优化这两个方面,以便为
fc
alpha
找到最佳的通用拟合,我可以将其放入我的模型中。
delta
是标准化的
alpha
?如果是这种情况,我如何进行反向计算以找到
alpha
的实际值?那么
fc
呢?再一次,我为自己无知而感到抱歉。我只是想把我的脑袋绕过去。我为浪费你的时间感到难过,因为我显然不配。
def objective(fc, alpha):

    poptRI, pcovRI = curve_fit(CCRI, f_exp, e_exp, p0=(fc, alpha))

    poptiQ, pcoviQ = curve_fit(CCiQ, f_exp, iq_exp, p0=(fc, alpha))

    delta = linalg.norm(poptiQ - poptRI)
    return delta