我试着用Scipy的Optimize运行一些曲线拟合。我不使用polyfit,因为我想确保曲线是单调的,考虑到我的关系。假设硫和温度之间有如下关系:
sulphur = array([ 71., 82., 50., 113., 153., 177., 394., 1239., 2070., 2662., 3516., 4000., 4954., 6314.])
temperature = array([ 70., 90., 140., 165., 210., 235., 265., 330., 350., 390., 410., 435., 540., 580.])
我想找到一条曲线来拟合这种单调递增的关系。在
我已经找到了一些代码,这就是我所拥有的:我计算多项式并将其用于目标函数,并且我约束一阶导数对于每个点都是正的。为了加快操作速度,我还使用polyfit值作为x0:
^{pr2}$但是,优化总是返回:
fun: 4.0156824919527855e+23
jac: array([0.00000000e+00, 0.00000000e+00, 7.02561542e+17, 3.62183986e+20])
message: 'Inequality constraints incompatible'
nfev: 6
nit: 1
njev: 1
status: 4
success: False
x: array([ -111.35802358, 1508.06894349, -2969.11149743, 2223.26354865])
我试着规范化(比如sul_norm=sul/max(sul)起作用),这样优化就成功地进行了,但是我想避免这样做(我必须在某一点上反转函数,然后回到原始值时会变得混乱)。而且,在我看来,这种关系是非常基本的,温度和硫之间的值在不同的尺度上并不是那么极端。可能是什么?谢谢!在
这里有各种各样的限制问题:首先是求解器的选择,这会极大地影响到你可以做什么样的优化(约束、有界等)。 除此之外,在您的例子中,您对参数感兴趣,并处理一个预定义的集
(x, y)
,因此您应该以多维的方式处理数据,以便进行与(x,y)
相关的计算。但是,据我所知,您使用的约束定义适用于一维输出。因此,正如SO-question所示,使用梯度是个好主意。在不幸的是,当在您的案例中进行测试时,结果并不能让我信服,尽管运行了没有错误的代码。在修改了你的代码之后,我设法找到了一个不错的解决方法,但我不确定是否是最好的。我的想法是使用
Nelder-Mead Solver
并使用一个等式约束来确保你的导数向量都是正的。代码如下:输出:
^{pr2}$绘图:
相关问题 更多 >
编程相关推荐