es.davy.ai

Preguntas y respuestas de programación confiables

¿Tienes una pregunta?

Si tienes alguna pregunta, puedes hacerla a continuación o ingresar lo que estás buscando.

Optimización no lineal con scipy.optimize.minimize utilizando matrices y vectores como variables de decisión.

Tengo un problema de optimización no lineal que utiliza 3 variables de decisión, una de estas variables es un número único (t), una es un vector con índice i (S_i) y una es una matriz (Q_i,j) con índices i y j. Actualmente estoy intentando utilizar scipy.optimize.minimize para modelar y resolver mi problema, pero no logro que funcione.

Debido a los múltiples índices, a menudo las restricciones deben cumplirse para todos los valores de algún índice. Mi modelo real es muy grande, así que consideremos este ejemplo que asumimos es no lineal:

Variable de decisión: Q_i,j

Objetivo:

minimizar Suma sobre todos los i y todos los j, Q_i,j

Restricción_1:

Q_i,j / 2 >= 10 para todos los i, para todos los j

Código actual que intento utilizar:

from scipy.optimize import minimize
import numpy as np

I = 5
J = 5
x0 = np.zeros(I*J)

def obj(Q_ij):
   Q_ijcp = np.reshape(Q_ijcp,(I,J))
   return sum(Q_ij[i,j] for i in range(I) for j in range(J))

def cons_1(Q_ij):
   Q_ijcp = np.reshape(Q_ijcp,(I,J))
   return (Q_ij[i,j] / 2 - 10 for i in range(I) for j in range(J))

b = (0, 100)
bounds = []
for i in range(I):
   for j in range(J):
      bounds.append(b)

constraint1 = {"type": "ineq", "fun": cons_1}
constraints = [constraint1]

solution = minimize(obj, x0=x0, bounds=bounds, constraints=constraints, method='SLSQP')

Según la guía del usuario, encontré que para cada restricción se debe hacer una definición de forma que pueda ser ingresada en el solucionador, lo cual intento hacer arriba, pero no funciona. ¿Cómo puedo modelar esto de manera que no tenga que hacer una definición para cada posible valor de i y j en Restricción_1? (De manera que no termine con 5 * 5 restricciones como en el caso de I=J=5)

¿O hay algún otro paquete con buena documentación/ejemplos que sea más fácil de usar en el caso de utilizar vectores y matrices con restricciones para sus índices?

Tags:  , , , ,

Answer

  1. Avatar for davy.ai

    Para evitar tener que definir una restricción para cada posible valor de i y j en Constraint_1, podemos usar la biblioteca numpy para crear una matriz booleana que verifique si la restricción se cumple para todos los valores de i y j, y luego usar la función numpy all() para asegurarse de que la restricción sea verdadera para todos los valores en la matriz. Así es como podemos modificar la función cons_1 para hacer esto:

    def cons_1(Q_ij):
        Q_ijcp = np.reshape(Q_ij,(I,J))
        return np.all(Q_ijcp/2 >= 10)
    

    Luego podemos eliminar el bucle sobre todos los valores de i y j en la variable bounds y simplificarlo a:

    bounds = [(0, 100)] * (I*J)
    

    Esto creará una lista de tuplas que contienen los límites inferior y superior para cada elemento de la variable de decisión, sin tener que recorrer todos los índices posibles.

    En cuanto a otros paquetes con buena documentación/ejemplos que sean más fáciles de usar en el caso de usar vectores y matrices con restricciones para sus índices, puedes considerar el uso de la biblioteca CVXPY. CVXPY te permite definir problemas de optimización en un formato más natural y matemático, y maneja las restricciones que involucran matrices y vectores con facilidad. Aquí tienes un ejemplo de cómo podrías usar CVXPY para resolver el mismo problema:

    import cvxpy as cp
    
    I = 5
    J = 5
    
    Q = cp.Variable((I,J))
    
    objective = cp.Minimize(cp.sum(Q))
    
    constraints = [Q[i,j]/2 >= 10 for i in range(I) for j in range(J)]
    
    problem = cp.Problem(objective, constraints)
    
    solution = problem.solve()
    

    Observa que en la versión de CVXPY, no necesitamos definir una función separada para el objetivo y cada restricción. En su lugar, podemos escribirlos en un formato más natural y matemático, y CVXPY se encargará de convertirlos en la forma adecuada para el solucionador. Además, podemos usar las reglas de transmisión de numpy para manejar restricciones que involucren matrices y vectores, lo que hace que el código sea más conciso y fácil de leer.

Comments are closed.