使用Mystic进行优化和线性不等式

时间:2019-01-05 18:48:12

标签: python optimization constraints mystic

我正在使用相当复杂的目标函数,通过更改4个参数将其最小化。不久前,我决定使用Python框架Mystic,该框架无缝地允许我对复杂的不等式(我需要)使用惩罚。

但是,Mystic有一种不太明显的方式来分配硬约束(不是不等式和非约束性约束,仅是参数之间的线性不等式),甚至还有不太明显的方式来处理它们。

我所有的4个参数的上下限都是有限的。我想将线性不等式添加为这样的硬约束:

def constraint(x):  # needs to be <= 0
    return x[0] - 3.0*x[2]

但是,如果我尝试以这种方式使用Mystic:

from mystic.solvers import fmin_powell
xopt = fmin_powell(OF, x0=x0, bounds=bounds, constraints=constraint)

然后,Mystic坚持要求先调用目标函数来解决约束,然后再进行实际优化。由于目标函数值对上面定义的约束函数没有影响,也没有任何影响,所以我不确定为什么会这样。上面定义的约束函数只是告诉Mystic,超参数搜索空间的区域应该超出限制。

我已经仔细检查了Mystic文件夹中的所有示例,并且偶然发现了定义硬约束的另一种方法:使用惩罚函数,然后调用魔术方法“ as_constraint”将其“转换”为约束。不幸的是,所有这些示例几乎都是这样:

from mystic.solvers import fmin_powell
from mystic.constraints import as_constraint
from mystic.penalty import quadratic_inequality

def penalty_function(x): # <= 0.0
    return x[0] - 3.0*x[2]

@quadratic_inequality(penalty_function)
def penalty(x):
    return 0.0

solver = as_constraint(penalty)

result = fmin_powell(OF, x0=x0, bounds=bounds, penalty=penalty)

这是魔术路线:

solver = as_constraint(penalty)

我看不到它在做什么-不再使用 solver 变量。

因此,对于一个问题:是否有任何方法可以定义Mystic中的线性不等式,而这些线性不等式不涉及昂贵的约束预求解,而只是告诉Mystic排除搜索空间的某些区域?

预先感谢您的任何建议。

安德里亚。

1 个答案:

答案 0 :(得分:0)

mystic的作用是映射其搜索的空间,因此您正在“内核转换”的空间上进行优化(以使用机器学习术语)。如果您知道这意味着,可以将约束视为应用运算符。因此,y = f(x)在某些约束x' = c(x)下变成y = f(c(x))。这就是为什么优化程序在评估目标之前先评估约束条件的原因。

因此您可以建立这样的约束:

>>> import mystic.symbolic as ms
>>> equation = 'x1 - 3*a*x2 <= 0'
>>> eqn = ms.simplify(equation, locals=dict(a=1), all=True)
>>> print(eqn)
x1 <= 3*x2
>>> c = ms.generate_constraint(ms.generate_solvers(eqn, nvars=3))
>>> c([1,2,3])
[1, 2, 3]
>>> c([0,100,-100])
[0, -300.0, -100]

或者如果您有多个:

>>> equation = '''
... x1 > x2 * x0     
... x0 + x1 < 10
... x1 + x2 > 5
... '''
>>> eqn = ms.simplify(equation, all=True)
>>> print(eqn)
x1 > -x2 + 5
x0 < -x1 + 10
x1 > x0*x2
>>> import mystic.constraints as mc
>>> c = ms.generate_constraint(ms.generate_solvers(eqn), join=mc.and_)
>>> c([1,2,3])
[1, 3.000000000000004, 3]
相关问题