Я пытаюсь использовать scipy
для решения нетривиальной оптимизации. У меня 6-мерная проблема. Функция, которую я пытаюсь оптимизировать, не является линейной.
Я думаю, что эту проблему нелинейной оптимизации можно решить с помощью scipy.optimize.minimize
, см. https://docs.scipy.org/doc/scipy/reference/tutorial/optimize.html#constrained-minimization-of-multivariate-scalar-functions-minimize Документация показывает, что ограничения могут быть обработаны по одному:
cons = ({'type': 'eq',
'fun' : lambda x: np.array([x[0]**3 - x[1]]),
'jac' : lambda x: np.array([3.0*(x[0]**2.0), -1.0])},
{'type': 'ineq',
'fun' : lambda x: np.array([x[1] - 1]),
'jac' : lambda x: np.array([0.0, 1.0])})
В моем случае мне нужно 12 ограничений: один максимум и одна минута для каждого измерения. Я также хочу что-то, что я мог бы обобщить на большее или меньшее количество измерений, поэтому я не хочу вводить все ограничения вручную. Предполагая, что мои минимумы и максимумы находятся в двух массивах. Если я использую цикл, такой как:
for i in range(6):
grad_min = np.zeroes(6)
grad_max = np.zeroes(6)
grad_min[i] = +1.
grad_max[i] = -1
cons_min = {'type': 'ineq',
'fun' : lambda x: np.array([x[i] - min[i]),
'jac' : lambda x : grad_min})
cons_max = {'type': 'ineq',
'fun' : lambda x: np.array([-x[i] + max[i]),
'jac' : lambda x : grad_max})
cons = cons + (cons_min,cons_max)
Но из-за отсутствия закрытия функций lambda
в Python это не получится, будет применена только последняя (i=5
). Я ищу другой дизайн, где я могу определить все ограничения одновременно, мне нужно что-то использовать с замыканием ..