Reputation: 273
I have two arrays, one with amounts and the other with risk. I want to basically minimize the sum of the amounts and at the same time keep the sum of the risks the same. To do this, I want to multiply the Amount and Risk with a array of weights (which needs to be solved for).
from scipy.optimize import minimize
import numpy as np
#Array of Amounts
Amount = np.array([10000000,-2000000,400000000,60000000])
#Array of Risk
Risk = np.array([-10000,5000,-20000,500])
#Minimize the sum of Amounts
def Objective(weights):
x = weights * Amount
return np.sum(x)
#While keeping the sum of Risks constant i.e Sum of New Weighted Risk - Sum of Old weighted risk = 0
def Cons1(weights):
x = weights*Risk
return np.sum(x)-np.sum(Risk)
#Create Constraint
cons = ({'type': 'eq', 'fun':Cons1})
#Give Initial Guess
guess = np.array([0.25,0.25,0.25,0.25])
#Minimize
minimize(Objective,guess,constraints=cons)
The result I get is:
fun: -2.1834331315418437e+18
jac: array([0., 0., 0., 0.])
message: 'Singular matrix C in LSQ subproblem'
nfev: 18
nit: 3
njev: 3
status: 6
success: False
x: array([ 9.32859191e+09, -4.14243499e+09, -4.78072085e+09, -6.21192636e+09])
When I use the solver on Excel (Simplex LP), I get a viable result:
Using guess weights :
Can anyone tell me what I'm doing wrong here?
Upvotes: 0
Views: 677
Reputation: 46
As Erwin Kalvelagen correctly stated, it is a linear problem. In order to document the solution, I used linprog
import numpy as np
from scipy.optimize import linprog
#Inputs into the Equation
#We want to minimize Amount and keep Risk constant
#Input Amount
Amount=np.array([10000000,-2000000,400000000,60000000])
#Input Risk
Risk = np.array([[-10000,5000,-20000,500]])
c= Amount
A_eq = Risk
b_eq = np.sum(A_eq)
linprog(c,A_eq=A_eq,b_eq=b_eq)
I get the correct result:
fun: 24500000.0
message: 'Optimization terminated successfully.'
nit: 2
slack: array([], dtype=float64)
status: 0
success: True
x: array([ 2.45, 0. , 0. , 0. ])
Upvotes: 3