查找全局最小值(SciPy)并将其显示在3D图形上

时间:2019-03-08 08:02:35

标签: python python-3.x scipy jupyter-notebook

我有两个变量的函数,我需要找到全局最小值。还要构建3D图形并在图形上显示全局最小值(一个点)。但是我得到的是第二个数字而不是一点。我使用Jupyter Notebook。我的代码是:

import numpy as np
from matplotlib import pyplot as plt
from scipy import optimize
from mpl_toolkits.mplot3d import Axes3D

fig = plt.figure(figsize=(10,10))
axes = fig.gca(projection='3d')

def f(x, y):
    return (np.exp(np.sqrt(x**2 + y**2)))

y = x = np.linspace(-3, 3, 50)

x, y = np.meshgrid(x, y)
z = f(x,y)

# optimization
optimize.minimize(f, -3, args=(3)) # maybe something is wrong right here
optimization = optimize.minimize(f, -3, args=(3))


surf = axes.plot_surface(x, y, z, cmap='coolwarm',
                       linewidth=0, antialiased=False)

surf1 = axes.plot_surface(x, y, f(optimization.x,y), cmap='coolwarm',
                       linewidth=0, antialiased=False)

axes.set_xlabel('Ось X')
axes.set_ylabel('Ось Y')
axes.set_zlabel('Ось Z')

plt.show()

1 个答案:

答案 0 :(得分:0)

问题是您在一个轴上优化了曲面,仅在脚本中生成了另一个曲面图。

您可以通过迭代优化每个轴来找到解决方案。在我下面提供的解决方案中,它可以为您的示例工作,但是为更复杂的函数(即非凸函数)找到全局最优值将需要更多的迭代才能收敛。 (可能还有more subtle gradient descent method

请注意,我使用轮廓3D代替plot_surface可以更好地可视化绘制的点。

import numpy as np
from matplotlib import pyplot as plt
from scipy import optimize
from mpl_toolkits.mplot3d import Axes3D

fig = plt.figure(figsize=(10,10))
axes = fig.gca(projection='3d')

def f(x, y):
    return (np.exp(np.sqrt(x**2 + y**2)))

y = x = np.linspace(-3, 3, 50)

x, y = np.meshgrid(x, y)
z = f(x,y)


# optimization x
optimization = optimize.minimize(f, [-3], args=(-3,)) 
best_x = optimization.x

# optimization y
optimization = optimize.minimize(lambda x,y: f(y,x), [-3], args=(-3,))
best_y = optimization.x

#surf = axes.plot_surface(x, y, z, cmap='coolwarm',linewidth=0, antialiased=True)
surf = axes.contour3D(x, y, z, 50,  cmap='coolwarm',)
axes.scatter3D([best_x], [best_y], [f(best_x, best_y)], s=[100], c="g");


axes.set_xlabel('Ось X')
axes.set_ylabel('Ось Y')
axes.set_zlabel('Ось Z')

plt.show()

enter image description here]