pythonreshapemosek

How do I reshape variables in MOSEK


I am trying to convert an optimization code written in MATLAB CVX to Python code that directly calls the solver MOSEK. My optimization consists of the following type of equation:

||Ax-b|| + regularizer.

x is a three-dimensional variable whose optimal value needs to be evaluated. I define A as a function in MATLAB as follows:

function D = A(X)   

n = size(X,1);
m = size(X,2);
nim = size(X,3);
for t = 1:nim
    temp = X(:,:,t);
    D(:,:,t) = squeeze(sum(sum(reshape(temp,7,19,7,19),1),3));
end
end

And so,||Ax-b|| in MATLAB CVX becomes

norm((vec(A(x)-b)))

Now, when I convert to python directly calling MOSEK, I write:

def lseReg(b,I,n,m,d,n1,m1,alpha,beta):
    M = Model("LSE-REG")
    x = M.variable("x", [n,m,d] )
    t = M.variable("t")
    
    y = M.variable("y",[n1,m1,d])
    for i in range(0,d):
        temp = x.slice([0,0,i],[n,m,i])
        temp2 = Var.reshape(temp,[19,7,19,7])
        y.slice[[0,0,i],[n1,m1,i]] =  Expr.sum(Expr.sum(temp2,3),1)
        
    r = Expr.sub(b,y)
    M.constraint(Expr.vstack(0.5,t,r),Domain.inRotatedQCone())
    t2 = M.variable("t2")
    r2 = Expr.sub(I,Expr.sum(x,2))
    M.constraint(Expr.vstack(0.5,t2,r2),Domain.inRotatedQCone())
    #the Objective
    ObjExpr1 = t.asExpr()
    ObjExpr2 = t2.asExpr()
    ObjExpr3 = Expr.mul(alpha,lassoVar(M,x,n,m,d))
    ObjExpr4 = Expr.mul(beta,lassoTV(M,x,n,m,d))
    objExpr = Expr.add(ObjExpr1,ObjExpr2,ObjExpr3,ObjExpr4)
    M.objective(ObjectiveSense.Minimize,objExpr)
    return M

However, I get the error:

  File "C:\Users\Anaconda\lib\site-packages\mosek\fusion\impl\_implementation.py", line 13779, in reshape
    return mosek_fusion_Var._reshape_alt_Lmosek_4fusion_4Variable_2_3I(*args)

  File "C:\Users\Anaconda\lib\site-packages\mosek\fusion\impl\_implementation.py", line 13967, in _reshape_alt_Lmosek_4fusion_4Variable_2_3I
    _1 = mosek_fusion_Var._reshape_Lmosek_4fusion_4Variable_2_3I(_0,_1)

  File "C:\Users\Anaconda\lib\site-packages\mosek\fusion\impl\_implementation.py", line 13976, in _reshape_Lmosek_4fusion_4Variable_2_3I
    return (_0._reshape__3I(_1))

  File "C:\Users\Anaconda\lib\site-packages\mosek\fusion\impl\_implementation.py", line 10897, in _reshape__3I
    raise mosek_fusion_LengthError._ctor_S("Shape size does not match variable size")

LengthError: Shape size does not match variable size

What am I doing wrong with this reshape?


Solution

  • This:

    x.slice([0,0,i],[n,m,i])

    will give you an object of size 0, you probably meant

    x.slice([0,0,i],[n,m,i+1])

    Remember that the "last" index is the one 1 behind the last element of the slice you want.

    You cannot assign things to a slice, this is illegal:

    y.slice[[0,0,i],[n1,m1,i]] =

    Instead you probably want to make a constraint.

    Those are the general comments that may be useful for others. We are aware that you sent the problem to MOSEK support and we are going to answer there with more details specific to your other questions.