Я впервые задаю вопрос здесь, поэтому, пожалуйста, потерпите меня. Теперь я «играл» с функцией минимизации и наткнулся на что-то странное.
Настройка проста, все, что я хочу сделать, это минимизировать евклидову норму вида:
sqrt [(x1 -a1) ^ 2 + (x2 -a2) ^ 2 + (x3 -a3) ^ 2 + (x4 -a4) ^ 2]
Где x - переменные, а a - фиксированные числа, константы. Конечно, решение простое, xi = ai для i = 1,2,3,4; и значение функции равно нулю.
Теперь, когда я делаю этот код в python, все работает отлично:
import numpy as np
from scipy.optimize import minimize
def w(x):
a = np.array([[0,1,1,0]]).T
return np.sqrt((x[0]-a[0])**2 + (x[1]-a[1])**2 + (x[2]-a[2])**2+(x[3]-a[3])**2)
np.random.seed(1)
x0 = np.random.random((4,1))
min_fun1 = minimize(w,x0,method='nelder-mead',options={'xatol': 1e-8, 'disp': True})
print(min_fun1.fun)
print(min_fun1.x)
Как я уже сказал, это работает просто отлично. Значение функции равно нулю и xi = ai. Но когда я пытаюсь установить проблему с помощью функции np.linlag.norm, это становится странным. Например, когда я запускаю этот код:
def y(x):
a = np.array([[0,1,1,0]]).T
return np.linalg.norm(x-a)
min_fun0 = minimize(y,x0,method='nelder-mead',options={'xatol': 1e-8, 'disp': True})
min_fun0.fun
min_fun0.x
Похоже, что оптимизация застревает, значение функции равно 2 и xi = 0,5, что, очевидно, неверно.
Более того, если я попытаюсь сделать это с помощью скалярного произведения, результат будет другим, но все же неправильным:
def v(x):
a = np.array([[0,1,1,0]]).T
return np.sqrt(np.dot((x-a).T,(x-a)))
min_fun2 = minimize(v,x0,method='nelder-mead',options={'xatol': 1e-8, 'disp': True})
min_fun2.fun
min_fun2.x
Что я смог понять, так это то, что он как-то связан с «типом» объекта. Например, no.linalg.norm возвращает float64, и для примера, который работает, это ndarray с размером 1. Поэтому я меняю «тип» для результата no.linalg.norm, чтобы он соответствовал ndarray размеру 1, но проблема остается.