我试图理解“dogleg”方法在Python的^{
根据注释,dogleg方法需要Jacobian和Hessian参数。为此,我使用^{
import numpy as np
from scipy.optimize import minimize
from numdifftools import Jacobian, Hessian
def fun(x,a):
return (x[0] - 1)**2 + (x[1] - a)**2
x0 = np.array([2,0]) # initial guess
a = 2.5
res = minimize(fun, x0, args=(a), method='dogleg',
jac=Jacobian(fun)([2,0]), hess=Hessian(fun)([2,0]))
print(res)
编辑:
如果我按照下面的帖子的建议做出改变
res = minimize(fun, x0, args=a, method='dogleg',
jac=Jacobian(lambda x: fun(x,a)),
hess=Hessian(lambda x: fun(x,a)))
我得到一个错误TypeError: <lambda>() takes 1 positional argument but 2 were given
。我做错什么了?
同样,在初始猜测x0
时计算雅可比和海森是否正确?
这个错误来自对
Jacobian
和Hessian
的调用,而不是minimize
。用Jacobian(lambda x: fun(x, a))
替换Jacobian(fun)
和类似的Hessian
应该可以做到(因为现在被区分的函数只有一个向量参数)。还有一件事:
(a)
就是a
,如果你想让它成为元组,就使用(a,)
。我知道这是一个有趣的例子,但我想指出,使用
Jacobian
或Hessian
这样的工具来计算导数而不是派生函数本身是相当昂贵的。例如,使用您的方法:但是你可以这样计算导数函数:
如你所见,速度快了将近50倍。它开始变得越来越复杂。因此,不管有多困难,我总是试图自己显式地导出函数。一个有趣的例子是Inductive Matrix Completion的基于内核的实现。
与显式推导和利用这些函数相比,用这个方程计算梯度和hessian是极不合理的。所以正如@bnaul所指出的,如果你的函数有封闭形式的导数,你真的想计算和使用它们。
相关问题 更多 >
编程相关推荐