繁体   English   中英

scipy最小化不等式约束函数

[英]scipy minimize inequality constraint function

我需要限制自己的损失,以便预测始终是积极的。 所以我有:

x = [1.0,0.64,0.36,0.3,0.2]
y = [1.0,0.5,0.4,-0.1,-0.2]
alpha = 0

def loss(w, x, y, alpha):
    loss = 0.0
    for y_i,x_i in zip(y,x):
        loss += ((y_i - np.dot(w,x_i)) ** 2)
    return loss + alpha * math.sqrt(np.dot(w,w))

res = minimize(loss_new_scipy, 0.0, args=(x, y, alpha))

现在我想添加约束,但是我发现大多数约束是x在边界之间,而不是np.dot(w,x)>= 0这样的约束看起来如何?

编辑:我想在scipy.optimize.minimize函数中使用constraints参数,所以我认为它应该看起来像这样:

def con(w,x):
    loss = 0.0
    for i_x in x:
         loss += (np.dot(w, i_x))
    return loss


cons = ({'type': 'ineq', 'fun': con})
res = minimize(loss_new_scipy, 0.0, args=(x, y, alpha), constraints=cons)

我也为简单起见删除了第二个约束

EDIT2:我将问题更改为以下内容:约束为w * x必须大于1,并且还将目标更改为所有负数。 我还更改了args,因此现在可以运行:

x = np.array([1.0,0.64,0.36,0.3,0.2])
y = [-1.0,-0.5,-0.4,-0.1,-0.2]
alpha = 0

def con(w,x,y,alpha):
    print np.array(w*x)
    return np.array((w*x)-1).sum()


cons = ({'type': 'ineq', 'fun': con,'args':(x,y,alpha)})

def loss_new_scipy(w, x, y, alpha):
    loss = 0.0
    for y_i,x_i in zip(y,x):
        loss += ((y_i - np.dot(w,x_i)) ** 2)
    return loss + alpha * math.sqrt(np.dot(w,w))

res = minimize(loss_new_scipy, np.array([1.0]), args=(x, y, alpha),constraints=cons)
print res

但是不幸的是,w的结果是2.0,这确实是正数,并且看起来像是约束条件的帮助,因为它距离将函数拟合到目标还很远,但是预测w * x并不都超过1.0

EDIT3:我刚刚意识到我的预测总和-1现在等于0,但是我希望每个预测都大于1.0,所以在w = 2.0的情况下,

w*x = [ 2.00000001  1.28000001  0.72        0.6         0.4       ] 

(w*x) - 1 = [ 1.00000001  0.28000001 -0.28       -0.4        -0.6       ]

该总和等于0.0,但我希望所有预测w*x都大于1.0,因此w*x所有5个值应至少为1.0

如果我正确理解您的EDIT2,则您尝试根据实数参数w (其中xy是向量)的函数来最小化|y - w*x|^2 ,并限制w*x所有分量都大于1 。

现在, |y - w*x|^2的表达式在w是二次的,因此它具有定义明确的全局最小值(在w^2前面的因子为正)。 不过,在各组分的约束w*x有效地施加的最小允许值w (因为x是固定的),这是在这种情况下, 5 由于二次(无约束)函数|y - w*x|^2的全局最小值针对您的特定情况,围绕np.dot(y,x)/np.dot(x,x)=-0.919 ,因此该函数为为单调增加的w>=5 ,因此值5表示约束最小...

为了用您的代码得到这个答案,必须修复约束。 在您的情况下,您将w*x所有分量相加了1。在这里,然而,可能会发生一个特定分量远大于1的情况,因此,它对总和的贡献可能会掩盖仅比其小一点的其他分量1(例如,如果x=[2, 0.25]w=2 ,则w*x-1=[3,-0.5]并且即使违反了约束,总和也为正)。 为了纠正这一点,可以仅求和w*x-1那些为负的分量,即违反约束的那些:

def con(w,x,y,alpha):
    return np.minimum(w*x - 1, 0).sum()

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM