我需要在高维空间中优化标量函数。函数随着参数的变化而变化很快,因此渐变的(绝对值)很大。 scipy.optimize.minimize
中的优化器失败,因为最小化过程采用过大的步骤。以下代码使用简单的二次函数说明了问题。
from scipy.optimize import minimize
def objective(x, scalar=1):
"""
Quadratic objective function with optional scalar.
"""
# Report function call for debugging
print "objective({}, scalar={})".format(x, scalar)
# Return function value and gradient
return x ** 2 * scalar, 2 * x * scalar
# This optimisation succeeds
print minimize(objective, 1, jac=True)
# This optimisation fails
print minimize(objective, 1, (1e8, ), jac=True)
当然,我可以手动重新调整感兴趣函数的值和梯度,但我想知道是否有一种推荐的方法来最小化这些函数,例如:指定学习率。
答案 0 :(得分:3)
对于大型非线性优化问题,通常会注意(至少)四件事:
一些更高级的解算器可能会为自动缩放提供一些支持。然而,非线性问题的缩放并不容易,因为雅可比会发生变化(一些通常可用的策略是:仅缩放线性部分,在开始时基于初始值缩放线性+非线性部分,或者在期间重新缩放问题迭代过程)。线性求解器在这方面工作更容易(雅可比矩阵是常数,因此我们可以在开始时缩放一次)。 Scipy.optimize.minimize
不是最先进的,所以我鼓励你自己扩展(通常你只能在求解器开始之前执行此操作;在某些情况下,你甚至可以停止求解器重新缩放,然后再次使用求解器最后一点作为初始值 - 这听起来很疯狂,但这个技巧帮了我几次)。良好的初始点和良好的界限在这方面也有帮助(为了使求解器保持在可以可靠地评估函数和梯度的合理区域)。最后,模型重构有时可以帮助提供更好的缩放(通过乘法取代除法,取日志等)。