scipy.optimize 陷入局部极小值。我能做什么?
scipy.optimize get's trapped in local minima. What can I do?
from numpy import *; from scipy.optimize import *; from math import *
def f(X):
x=X[0]; y=X[1]
return x**4-3.5*x**3-2*x**2+12*x+y**2-2*y
bnds = ((1,5), (0, 2))
min_test = minimize(f,[1,0.1], bounds = bnds);
print(min_test.x)
我的函数 f(X)
在 x=2.557, y=1
处有一个局部最小值,我应该可以找到它。
上面显示的代码只会在 x=1
处给出结果。我尝试过不同的公差和所有三种方法:L-BFGS-B、TNC 和 SLSQP。
这是我到目前为止一直在看的线程:
Scipy.optimize: how to restrict argument values
我该如何解决这个问题?
我正在使用 Spyder(Python 3.6).
您刚刚遇到局部优化问题:它在很大程度上取决于您传入的起始(初始)值。如果您提供 [2, 1]
,它将找到正确的最小值。
常见的解决方案是:
在你的边界内随机开始的循环中使用你的优化
import numpy as np
from numpy import *; from scipy.optimize import *; from math import *
def f(X):
x=X[0]; y=X[1]
return x**4-3.5*x**3-2*x**2+12*x+y**2-2*y
bnds = ((1,3), (0, 2))
for i in range(100):
x_init = np.random.uniform(low=bnds[0][0], high=bnds[0][1])
y_init = np.random.uniform(low=bnds[1][0], high=bnds[1][1])
min_test = minimize(f,[x_init, y_init], bounds = bnds)
print(min_test.x, min_test.fun)
使用可以摆脱局部极小值的算法,我可以推荐scipy的basinhopping()
使用全局优化算法并将其结果用作局部算法的初始值。建议使用 NLopt 的 DIRECT
或 MADS 算法(例如 NOMAD
)。 scipy、shgo
还有一个我还没试过
尝试scipy.optimize.basinhopping
。它只是多次重复您的最小化过程并获得多个局部最小值。最小的那个是全局最小的。
minimizer_kwargs = {"method": "L-BFGS-B"}
res=optimize.basinhopping(nethedge,guess,niter=100,minimizer_kwargs=minimizer_kwargs)
from numpy import *; from scipy.optimize import *; from math import *
def f(X):
x=X[0]; y=X[1]
return x**4-3.5*x**3-2*x**2+12*x+y**2-2*y
bnds = ((1,5), (0, 2))
min_test = minimize(f,[1,0.1], bounds = bnds);
print(min_test.x)
我的函数 f(X)
在 x=2.557, y=1
处有一个局部最小值,我应该可以找到它。
上面显示的代码只会在 x=1
处给出结果。我尝试过不同的公差和所有三种方法:L-BFGS-B、TNC 和 SLSQP。
这是我到目前为止一直在看的线程:
Scipy.optimize: how to restrict argument values
我该如何解决这个问题?
我正在使用 Spyder(Python 3.6).
您刚刚遇到局部优化问题:它在很大程度上取决于您传入的起始(初始)值。如果您提供 [2, 1]
,它将找到正确的最小值。
常见的解决方案是:
在你的边界内随机开始的循环中使用你的优化
import numpy as np from numpy import *; from scipy.optimize import *; from math import * def f(X): x=X[0]; y=X[1] return x**4-3.5*x**3-2*x**2+12*x+y**2-2*y bnds = ((1,3), (0, 2)) for i in range(100): x_init = np.random.uniform(low=bnds[0][0], high=bnds[0][1]) y_init = np.random.uniform(low=bnds[1][0], high=bnds[1][1]) min_test = minimize(f,[x_init, y_init], bounds = bnds) print(min_test.x, min_test.fun)
使用可以摆脱局部极小值的算法,我可以推荐scipy的
basinhopping()
使用全局优化算法并将其结果用作局部算法的初始值。建议使用 NLopt 的
DIRECT
或 MADS 算法(例如NOMAD
)。 scipy、shgo
还有一个我还没试过
尝试scipy.optimize.basinhopping
。它只是多次重复您的最小化过程并获得多个局部最小值。最小的那个是全局最小的。
minimizer_kwargs = {"method": "L-BFGS-B"}
res=optimize.basinhopping(nethedge,guess,niter=100,minimizer_kwargs=minimizer_kwargs)