Python CVXPY约束公式
我正在尝试使用CVXPY解决Stephen Boyd提出的等周问题(7.14)。问题是: 约束代码如下所示:Python CVXPY约束公式,python,mathematical-optimization,cvxpy,Python,Mathematical Optimization,Cvxpy,我正在尝试使用CVXPY解决Stephen Boyd提出的等周问题(7.14)。问题是: 约束代码如下所示: constraints = [ y[1] == 0, y[N] == 0, y[F] == yfixed[F], cp.abs(( y[i+2] - 2 * y[i+1] + y[i]) / h**2) <= C for i in np.arange(1,199) ] #not usin
constraints = [ y[1] == 0,
y[N] == 0,
y[F] == yfixed[F],
cp.abs(( y[i+2] - 2 * y[i+1] + y[i]) / h**2) <= C for i in np.arange(1,199) ] #not using the first constraint here
如何使用CVXPY约束中的循环?尝试将其拆分为两部分:
constraints = [ y[1] == 0,
y[N] == 0,
y[F] == yfixed[F] ] +
[ cp.abs(( y[i+2] - 2 * y[i+1] + y[i]) / h**2) <= C for i in np.arange(1,199) ]
约束=[y[1]==0,
y[N]==0,
y[F]==yfixed[F]]+
[cp.abs((y[i+2]-2*y[i+1]+y[i])/h**2)您需要根据cvxpy
的协议,用矩阵向量等式和不等式来表示约束。
为了详细说明,我可以在这个问题中看到三种约束:(我将假设基于0的索引,以便在剩下的答案中方便编程。)
将y
作为N+1
维度优化变量
定点相等约束:这些约束基本上将y
向量的一些索引设置为一组给定值。请注意,零边界条件y[0]==0
和y[N]==0
也属于此范围
周长约束:这是使用连续差分计算的。最后,我们将平方根的和加上差分的平方设置为小于L
。这部分可能是下面要编写的最复杂的部分cvxpy
协议
曲率约束:这也涉及类似于上述连续差分的计算,但编写起来要容易得多,因为您将看到这只是一个矩阵向量乘法类型的约束,类似于第一个约束
现在让我们用代码编写约束
必要进口:
将numpy导入为np
将cvxpy作为cp导入
将matplotlib.pyplot作为plt导入
来自scipy.linalg进口通告
1.平等限制:
这些基本上是从y
中选取一些索引,并将其设置为给定值。这可以实现如下:
def等式约束(N、F、vals):
'''
将y向量中的某些索引(F)设置为给定值。还设置
y[0]==0和y[N]==0。
返回E(矩阵)和E(向量),使E@y==E。
'''
E=np.zero((F.shape[0]+2,N+1))#'+2'用于选择y[0]和y[N]
e=np.零(F.形[0]+2)
E[0,0]=1
E[-1,-1]=1
如果F.shape[0]:
E[1:-1:1][np.arange(F.shape[0]),F]=1
e[1:-1:1]=VAL
返回E,E
E
是形状(F.shape[0]+2)x(N+1)
的二元矩阵,每行正好有一列设置为1,为(N+1)
维向量y
提供索引,E
包含y
的索引值
2.周界限制:
为此,我们需要y[i+1]-y[i]形式的连续差异
对于i=0,1,2,…,N-1
。请注意,我们可以类似地构造一个向量,将此N
连续差作为其元素。我们可以使用向量化计算轻松地对该向量执行平方根和其他操作。这里我们构造nx(N+1)
矩阵M
,当与y
相乘时,将给出N
差异
def长度矩阵(N):
'''
返回L,第一行为[-1,1,0,…,0],并滑动它
到右侧以获取以下行。
'''
val=np.array([-1,1])
偏移量=np.数组([0,1])
col0=np.零(N+1)
col0[offsets]=val
M=循环(col0).T[:-(len(val)-1)]
返回M
矩阵M
将是一个矩阵。我只是简单地将其转置并删除最后一行以获得所需的矩阵。您可以看到这一点以了解如何创建这样的矩阵。M
如下所示:
array([[-1., 1., 0., ..., 0., 0., 0.],
[ 0., -1., 1., ..., 0., 0., 0.],
[ 0., 0., -1., ..., 0., 0., 0.],
...,
[ 0., 0., 0., ..., 1., 0., 0.],
[ 0., 0., 0., ..., -1., 1., 0.],
[ 0., 0., 0., ..., 0., -1., 1.]])
3.曲率约束:
与上一个完全相同的矩阵计算。只需重复并沿行滑动[1,-2,1]
def curvature_constraints(N, C, h):
'''
Returns D and C_vec to be used as D @ y <= C and D @ y >= -C
as curvature constraints.
'''
val = np.array([1, -2, 1])
offsets = np.array([0, 1, 2])
col0 = np.zeros(N+1)
col0[offsets] = val
D = circulant(col0).T[:-(len(val) - 1)]
D /= h**2
C_vec = np.ones(D.shape[0]) * C
return D, C_vec
问题的制定和解决:
我将让您了解我是如何在制定约束时组装矩阵的,尤其是周长约束。这并不困难,但可能需要您进行一些练习,具体取决于您对矢量化的熟悉程度。该页面是一个非常好的起点
y=cp.Variable(N+1)
E、 E=等式约束(N,F,VAL)
M=长度矩阵(N)
D、 D=曲率约束(N,C,h)
约束=[
E@y==E,
h*cp.sum(cp.norm(cp.vstack([(M@y)/h,np.one(N)]),p=2,axis=0))试过了,无效语法根据CVXPYSee:谢谢你的解释。我发现DCP在曲率规则方面有点混乱。你能提出一些建议吗?我认为Stephen Boyd的凸优化讲座足以让你基本全面地理解。在那之后,你用cvxpy解决的问题越多,tr就越多你会发现的ICK和公式。你也可以学习cvxpy的教程页。好吧,它们真的很好地帮助你开始基本问题!@swag2198那本书有两位作者。
def curvature_constraints(N, C, h):
'''
Returns D and C_vec to be used as D @ y <= C and D @ y >= -C
as curvature constraints.
'''
val = np.array([1, -2, 1])
offsets = np.array([0, 1, 2])
col0 = np.zeros(N+1)
col0[offsets] = val
D = circulant(col0).T[:-(len(val) - 1)]
D /= h**2
C_vec = np.ones(D.shape[0]) * C
return D, C_vec