I'm trying to use GEKKO to solve some kind of the shop stock balance problem - the main goal is to determine which arrival (x) of goods per day will provide sufficient stock (Inv) in the store, taking into account sales (s) and demand (d).
So, my objective function is:
With restrictions:
See them in code below:
from gekko import GEKKO
m = GEKKO(remote=False)
n = 70 # Number of days, iterations
a = m.Param(144.846147/n) # coefficient for balance valuation
b = m.Param(417.33) # coefficient for deficit valuation
zero = m.Param(0.001)
receptions = [24, 31, 38, 45, 52, 59, 66] # Days when arrival expected
sales_coef = m.Param([0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 0, 1,
0, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0,
0, 1, 0, 0], integer=True) # Sales
demand_coef = m.Param([0.218, 0.218, 0.218, 0.218, 0.218, 0.218, 0.218, 0.218, 0.218, 0.218, 0.218, 0.218, 0.218, 0.218,
0.218, 0.218, 0.218, 0.218, 0.218, 0.218, 0.218, 0.206, 0.206, 0.206, 0.206, 0.206, 0.206, 0.206,
0.206, 0.206, 0.206, 0.206, 0.206, 0.206, 0.206, 0.206, 0.251, 0.251, 0.251, 0.251, 0.251, 0.251,
0.251, 0.251, 0.251, 0.251, 0.251, 0.251, 0.251, 0.251, 0.251, 0.251, 0.21, 0.21, 0.21, 0.21,
0.21, 0.21, 0.21, 0.21, 0.21, 0.21, 0.21, 0.21, 0.21, 0.21, 0.21, 0.21, 0.21, 0.21], integer=False) # Demand
x = m.Array(m.MV, n, lb=0, integer=True) # Arrival
y = m.Array(m.MV, n, lb=0, integer=True) # Balance
# Restrictions
for i in range(n):
if i + 1 in receptions: # if arrival expected
m.Equation(x[i] >= 0)
x[i].STATUS = 1
else:
x[i].VALUE = 0 # In other days arrival fixed to 0
x[i].STATUS = 0
if i > 0: # Restrictions for balance, except first day with initial value
y[i] = m.Intermediate(m.max2(y[i - 1] - sales_coef[i - 1], zero) + x[i])
else:
y[i].VALUE = 5 # Initial balance
y[i].STATUS = 0
m.Obj(a * m.sum(y) + b * m.sum([m.max2(demand_coef[i] - y[i], zero) for i in range(n)]))
m.options.SOLVER = 1
m.options.IMODE = 5
m.options.MAX_ITER = 1000
m.solve(disp=True)
print([(i + 1, yi) for i, yi in enumerate(y)])
I'm using APOPT (v1.0) and, as you can see, variables with integer=True are used for balancies and arrivals.
But when I look at the values of balancies y[i] in output, I can see, that for some days (when the deficit is expected), optimizer somehow selected float values for integer variable, for example:
(24, [1.0]), (25, [0.2059999]), (26, [0.2059999])
I expected, that type of variable will be taken into account when manipulating with variable. So, how is it possible? Have I miss some variables parameters, model options?

