linesearch的正方向导数

Dav*_*jad 12 scipy

scipy.optimize'linesearch的正方向导数'的含义是什么意思?

例如在fmin_slsqp中 http://docs.scipy.org/doc/scipy/reference/generated/scipy.optimize.fmin_slsqp.html

pv.*_*pv. 16

这些优化算法通常通过选择下降方向,然后对该方向执行线搜索来工作.我认为这个消息意味着优化器进入了一个位置,它无法找到目标函数值减小的方向(足够快),但也无法验证当前位置是否为最小值.


Dav*_*jad 13

我仍然不知道这意味着什么,但如何解决它.基本上,优化的函数需要返回一个较小的值.

F(x):
    ...
    return value / 10000000
Run Code Online (Sandbox Code Playgroud)

  • 更一般的答案是正在优化的功能很难缩放.我认为理想的是被优化的函数应该倾向于给出1-5范围内的平均值.对于我的用例,我不得不乘以1000. (2认同)
  • @Windstorm1981,如果您只缩放目标,那么解决方案值“x”应该是好的。但是,如果您还缩放了输入值,那么您必须在最后反转缩放以获得实际的解决方案。对于这些问题,实际上最好的方法是所有值(输入和目标)都缩放为 1 阶。最终需要付出一些努力来实现这种缩放和取消缩放,但如果优化问题很大,这应该会有所帮助收敛很多。 (2认同)

小智 5

为避免更改功能,您还可以尝试使用ftol和eps参数进行试验.将ftol更改为更高的值相当于将函数更改为更小的值.


Ken*_*HBS 5

您收到此错误的一种情况是

  1. x0超出您在 中定义的有效范围bounds
  2. 并且在 之外的值达到无约束最大值bounds

我将设置一个假设的优化问题,使用两个不同的初始值运行它并打印输出scipy.optimize

import numpy as np
from scipy import optimize

H = np.array([[2., 0.],
              [0., 8.]])

c = np.array([0, -32])

x0 = np.array([0.5, 0.5])    # valid initial value
x1 = np.array([-1, 1.1])     # invalid initial value

def loss(x, sign=1.):
    return sign * (0.5 * np.dot(x.T, np.dot(H, x)) + np.dot(c, x))

def jac(x, sign=1.):
    return sign * (np.dot(x.T, H) + c)

bounds = [(0, 1), (0, 1)]
Run Code Online (Sandbox Code Playgroud)

现在损失函数、梯度、x0 和边界都已准备就绪,我们可以解决问题:

def solve(start):
    res = optimize.minimize(fun=loss, 
                            x0=start, 
                            jac=jac, 
                            bounds=bounds,
                            method='SLSQP')
    return res



solve(x0)   # valid initial value
# fun: -27.999999999963507
# jac: array([ 2.90878432e-14, -2.40000000e+01])
# message: 'Optimization terminated successfully.'
# ...
#  status: 0
# success: True
# x: array([1.45439216e-14, 1.00000000e+00])

solve(x1)      # invalid initial value:
#  fun: -29.534653465326528
#  jac: array([ -1.16831683, -23.36633663])
#  message: 'Positive directional derivative for linesearch'
#  ...
#  status: 8
#  success: False
#  x: array([-0.58415842,  1.07920792])
Run Code Online (Sandbox Code Playgroud)

作为@pv。在接受的答案中指出,该算法无法验证这是最小值:

我认为这条消息意味着优化器进入了一个位置,它无法找到目标函数值减小的方向(足够快),但也无法验证当前位置是否为最小值。