GEKKO 无法为问题中的许多 if 语句找到解决方案

GEKKO can't find solution for many if-statements in the problem

我正在尝试解决一个优化问题,其中一个约束是一个选择 non-zero mass 材料并计算 属性 所选材料的函数。 一般来说,我混合了多种材料,我正在尝试优化混合计算不同的参数。其中一个参数是某些材料的总和 属性 仅适用于 non-zero 大量材料 - 基本上有很多 if 语句。 这是此类功能的示例。

from gekko import GEKKO
m = GEKKO()
m.options.SOLVER = 1

properties = [2, 4, 7, 3, 2, 9, 6, 2]
m1 = m.Var(0, lb=0, ub=1)
m2 = m.Var(0.5, lb=0, ub=1)
m3 = m.Var(0.1, lb=0, ub=1)
m4 = m.Var(0.2, lb=0, ub=1)
m5 = m.Var(0.4, lb=0, ub=1)
m6 = m.Var(0.1, lb=0, ub=1)
m7 = m.Var(0.3, lb=0, ub=1)
m8 = m.Var(0.1, lb=0, ub=1)

m.Equation(m1+m2+m3+m4 == 1.0)
m.Equation(m5 + m6 + m7 + m8 == 1.0)

vars = [m1, m2, m3, m4, m5, m6, m7, m8]

actual_score_materials = []
max_score_materials = []
for idx, material in enumerate(vars):
        is_nonzero = m.if3(-material, 1, 0)
        var = m.Intermediate(properties[idx] * is_nonzero)
        actual_score_materials.append(var)
        max_score_materials.append((properties[idx] + 10) * is_nonzero)

actual_score = m.sum(actual_score_materials)
max_score = m.sum(max_score_materials)

obj = m.Intermediate(actual_score / max_score / 0.8)

m.Minimize(obj)
m.solve()

问题是求解器无法为此类定义的问题找到任何解决方案(我尝试设置许多不同的起点但没有成功)。 GEKKO 有没有办法定义此类问题? 谢谢

尝试在 max_score 上设置下限。

max_score = m.Var(lb=0.01)
m.Equation(max_score == m.sum(max_score_materials))

没有这个下限,objective 函数是 NaN,表示它将 max_score 设置为零以最大化 objective。结果,优化器卡住了。在最优解处,max_score.value=[115].

from gekko import GEKKO
m = GEKKO()


properties = [2, 4, 7, 3, 2, 9, 6, 2]
m1 = m.Var(0, lb=0, ub=1)
m2 = m.Var(0.5, lb=0, ub=1)
m3 = m.Var(0.1, lb=0, ub=1)
m4 = m.Var(0.2, lb=0, ub=1)
m5 = m.Var(0.4, lb=0, ub=1)
m6 = m.Var(0.1, lb=0, ub=1)
m7 = m.Var(0.3, lb=0, ub=1)
m8 = m.Var(0.1, lb=0, ub=1)

m.Equation(m1+m2+m3+m4 == 1.0)
m.Equation(m5+m6+m7+m8 == 1.0)

vars = [m1, m2, m3, m4, m5, m6, m7, m8]

actual_score_materials = []
max_score_materials = []
for idx, material in enumerate(vars):
        is_nonzero = m.if3(-material, 1, 0)
        var = m.Intermediate(properties[idx] * is_nonzero)
        actual_score_materials.append(var)
        max_score_materials.append((properties[idx] + 10) * is_nonzero)

actual_score = m.sum(actual_score_materials)
max_score = m.Var(lb=0.01)
m.Equation(max_score == m.sum(max_score_materials))

obj = m.Intermediate(actual_score / max_score / 0.8)

m.Minimize(obj)

m.options.SOLVER = 1
m.solve()

这是求解器输出:

 --------- APM Model Size ------------
 Each time step contains
   Objects      :            2
   Constants    :            0
   Variables    :           59
   Intermediates:            9
   Connections  :           18
   Equations    :           53
   Residuals    :           44
 
 Number of state variables:             59
 Number of total equations: -           45
 Number of slack variables: -           16
 ---------------------------------------
 Degrees of freedom       :             -2
 
 * Warning: DOF <= 0
 ----------------------------------------------
 Steady State Optimization with APOPT Solver
 ----------------------------------------------
Iter:     1 I:  0 Tm:      0.00 NLPi:    7 Dpth:    0 Lvs:    2 Obj:  3.83E-01 Gap:       NaN
--Integer Solution:   4.00E-01 Lowest Leaf:   3.83E-01 Gap:   1.72E-02
Iter:     2 I:  0 Tm:      0.00 NLPi:    3 Dpth:    1 Lvs:    1 Obj:  4.00E-01 Gap:  1.72E-02
--Integer Solution:   3.80E-01 Lowest Leaf:   3.80E-01 Gap:   0.00E+00
Iter:     3 I:  0 Tm:      0.00 NLPi:    3 Dpth:    1 Lvs:    1 Obj:  3.80E-01 Gap:  0.00E+00
 Successful solution
 
 ---------------------------------------------------
 Solver         :  APOPT (v1.0)
 Solution time  :   3.800000000046566E-002 sec
 Objective      :   0.380434782608696     
 Successful solution
 ---------------------------------------------------