Objective function (including log functions) with optimal solution is not equal to cvx_optval

Hi, everyone. My problem is that the objective function with obtained optimal solution is not equal to cvx_optval.

Specifically, the optimization problem is a convex problem. There are only two variables X and Y in cvx code. The objective function is a sum_log like function. And there is a for-while iteration containing the convex problem. In each iteration, I use variable sum_r4 to calculate the objective function with the optimal solution, but it’s not equal to cvx_optval. I wonder whether cvx has obtained the real optimal solution in my case.

I have read several topics such as substituting log function with rel_entr_quad by CVXQUAD. Also using cvx 2.2 and mosek 9.1.9. However, it doesn’t work.

I give the complete matlab code as follows which is reproducible.

Thank you.

%% Parameters 
BW=180000;
K=15;
M=K;
N=K;

noise_density_dBm=-140;
noise=10^(noise_density_dBm/10)*BW;
Pu_max_dBm=24;%dBm
Pu_max=10^(Pu_max_dBm/10);
Pd_max_dBm=43;
Pd_max=10^(Pd_max_dBm/10);
Pu=Pu_max*ones(M,K);
Pd=Pu;

%% distance
radius=500;

theta_user=zeros(M,N);
d_user=zeros(M,N);

theta_U=random('uniform',0,2*pi,M,1);
d_U=random('uniform',100,radius,M,1); 

theta_D=random('uniform',0,2*pi,N,1);
d_D=random('uniform',100,radius,N,1);

H=zeros(M,N,K);

for i=1:M
    theta_user(i,:)=abs(theta_U(i)-theta_D);
end
theta_user(theta_user>pi)=2*pi-theta_user(theta_user>pi);
for x=1:M
    for y=1:N
    d_user(x,y)=sqrt(d_U(x)^2+d_D(y)^2-2*d_U(x)*d_D(y)*cos(theta_user(x,y)));
    end
end

fc=2e9;
lambda=3e8/fc;
PL=3; %pass loss 
d0=150;
sigma=3;

beta_BU_dB=-20*log10(lambda/(4*pi*d0))+10*PL*log10(d_U/d0)+sigma*randn(size(d_U));

beta_BU=10.^(-beta_BU_dB/10);

beta_BD_dB=-20*log10(lambda/(4*pi*d0))+10*PL*log10(d_D/d0)+sigma*randn(size(d_D));
beta_BD=10.^(-beta_BD_dB/10);

beta_user_dB=-20*log10(lambda/(4*pi*d0))+10*PL*log10(d_user/d0)+sigma*randn(size(d_user));
beta_user=10.^(-beta_user_dB/10);

h_bb_dB=100;

h_mk=sqrt(beta_BU).*(randn(M,K)+1j*randn(M,K))/sqrt(2);
h_nk=sqrt(beta_BD).*(randn(N,K)+1j*randn(N,K))/sqrt(2);
h_bbk=sqrt(10.^(-h_bb_dB/10))*(randn(1,K)+1j*randn(1,K))/sqrt(2);

for k=1:K
h_user=sqrt(beta_user).*(randn(M,N)+1j*randn(M,N))/sqrt(2);
H(:,:,k)=h_user;
end

%% Initial (Greedy) RB assignments to X and Y.
X_i=zeros(M,K);
G_u=abs(h_mk).^2;

for k=1:K
    mm=find(G_u(:,k)==max(G_u(:,k)));
    X_i(mm,k)=1;
end

Y_i=zeros(N,K);
G_d=abs(h_nk).^2;

for k=1:K
    mm=find(G_d(:,k)==max(G_d(:,k)));
    Y_i(mm,k)=1;
end

%% CVX: compute the optimal X and P for FD RBs
opt=[];sum_l=0;delta=1;time=0;
while delta>0.01
f2_i=M*sum(log2(noise+sum(Y_i.*Pd.*(abs(h_bbk).^2),1)))+sum(sum(log2(noise+sum((shiftdim((X_i').*ones(K,M,N),1)).*(shiftdim((Pu').*ones(K,M,N),1)).*(abs(H).^2),1))));
grad_x=squeeze(sum(shiftdim(Pu'.*ones(K,M,N),1).*(abs(H).^2)./(noise+sum(shiftdim(X_i'.*ones(K,M,N),1).*shiftdim(Pu'.*ones(K,M,N),1).*(abs(H).^2),1))/log(2),2));
gradx=reshape(grad_x,1,M*K);
grad_y=M*Pd.*(abs(h_bbk).^2)./(noise+sum(Y_i.*Pd.*(abs(h_bbk).^2),1))./log(2);
grady=reshape(grad_y,1,N*K);

cvx_begin 
cvx_solver mosek
variables X(M,K) Y(N,K) 
minimize(-(sum(sum( log(noise+repmat(sum(Y.*Pd.*(abs(h_bbk).^2.*ones(N,K)),1),M,1)+X.*Pu.*(abs(h_mk).^2))/log(2) ))+ ...
    sum(sum(  log(noise+ squeeze(sum(shiftdim(repmat((X.*Pu)',[1,1,N]),1).*(abs(H).^2),1)) +Y.*Pd.*(abs(h_nk).^2))/log(2) )) - ...
    (f2_i+gradx*(reshape(X-X_i,1,M*K))'+grady*(reshape(Y-Y_i,1,N*K))')));
subject to
X>=0
X<=1
Y>=0
Y<=1
sum(X,1)<=1
sum(X,2)==1
sum(Y,1)<=1
sum(Y,2)==1
cvx_end

sum_r3=sum(sum(log2(1+(X.*Pu.*(abs(h_mk).^2))./(noise+sum(Y.*Pd.*(abs(h_bbk).^2),1)))))+ ...
    sum(sum(log2(1+(Y.*Pd.*(abs(h_nk).^2))./(noise+squeeze(sum(shiftdim((X.*Pu)'.*ones(K,M,N),1).*(abs(H).^2),1))))));
sum_r4=-(sum(sum( log(noise+repmat(sum(Y.*Pd.*(abs(h_bbk).^2.*ones(N,K)),1),M,1)+X.*Pu.*(abs(h_mk).^2))/log(2) ))+ ...
    sum(sum(  log(noise+ squeeze(sum(shiftdim(repmat((X.*Pu)',[1,1,N]),1).*(abs(H).^2),1)) +Y.*Pd.*(abs(h_nk).^2))/log(2) )) - ...
    (f2_i+gradx*(reshape(X-X_i,1,M*K))'+grady*(reshape(Y-Y_i,1,N*K))'));
delta=abs(sum_r3-sum_l);
sum_l=sum_r3;
time=time+1;
if time>50
    break;
end

X_i=X;
Y_i=Y;
end

Maybe if you included the log output from CVX 2.2 with Mosek you would get an answer faster. It may take some time before we get around to run your code.

No problem, the log output is gven as follows.

Calling Mosek 9.1.9: 2310 variables, 900 equality constraints
For improved efficiency, Mosek is solving the dual problem.

MOSEK Version 9.1.9 (Build date: 2019-11-21 11:34:40)
Copyright © MOSEK ApS, Denmark. WWW: mosek.com
Platform: Windows/64-X86

Problem
Name :
Objective sense : min
Type : CONIC (conic optimization problem)
Constraints : 900
Cones : 450
Scalar variables : 2310
Matrix variables : 0
Integer variables : 0

Optimizer started.
Presolve started.
Linear dependency checker started.
Linear dependency checker terminated.
Eliminator started.
Freed constraints in eliminator : 0
Eliminator terminated.
Eliminator - tries : 1 time : 0.00
Lin. dep. - tries : 1 time : 0.00
Lin. dep. - number : 0
Presolve terminated. Time: 0.05
GP based matrix reordering started.
GP based matrix reordering terminated.
Problem
Name :
Objective sense : min
Type : CONIC (conic optimization problem)
Constraints : 900
Cones : 450
Scalar variables : 2310
Matrix variables : 0
Integer variables : 0

Optimizer - threads : 4
Optimizer - solved problem : the primal
Optimizer - Constraints : 450
Optimizer - Cones : 451
Optimizer - Scalar variables : 2311 conic : 1381
Optimizer - Semi-definite variables: 0 scalarized : 0
Factor - setup time : 0.02 dense det. time : 0.00
Factor - ML order time : 0.00 GP order time : 0.02
Factor - nonzeros before factor : 1.06e+04 after factor : 6.92e+04
Factor - dense dim. : 2 flops : 1.38e+07
Factor - GP saved nzs : 263 GP saved flops : 1.40e+05
ITE PFEAS DFEAS GFEAS PRSTATUS POBJ DOBJ MU TIME
0 1.9e+04 1.4e+01 9.0e+02 0.00e+00 3.725273696e+02 -5.226824993e+02 1.0e+00 0.09
1 3.4e+03 2.5e+00 3.8e+02 -1.00e+00 4.209702136e+03 3.319032658e+03 1.8e-01 0.25
2 1.2e+03 8.8e-01 2.2e+02 -9.99e-01 1.376159157e+04 1.288221478e+04 6.3e-02 0.27
3 7.5e+02 5.6e-01 1.8e+02 -9.87e-01 2.200780805e+04 2.114680970e+04 4.0e-02 0.27
4 5.1e+02 3.8e-01 1.4e+02 -9.20e-01 2.961451045e+04 2.880697221e+04 2.7e-02 0.28
5 4.0e+02 3.0e-01 1.0e+02 -5.80e-01 2.745572246e+04 2.675962214e+04 2.1e-02 0.28
6 2.6e+02 1.9e-01 6.0e+01 -1.90e-01 2.165667293e+04 2.113738160e+04 1.4e-02 0.30
7 1.8e+02 1.3e-01 3.7e+01 1.83e-01 1.688193109e+04 1.647995344e+04 9.6e-03 0.30
8 1.3e+02 9.9e-02 2.5e+01 3.97e-01 1.339520567e+04 1.307627091e+04 7.0e-03 0.31
9 1.1e+02 8.3e-02 2.0e+01 4.88e-01 1.146698555e+04 1.118635200e+04 5.9e-03 0.31
10 7.6e+01 5.7e-02 1.2e+01 6.01e-01 8.108484911e+03 7.903424890e+03 4.1e-03 0.33
11 6.5e+01 4.8e-02 9.5e+00 6.52e-01 6.765775501e+03 6.586250439e+03 3.5e-03 0.33
12 3.9e+01 2.9e-02 4.6e+00 7.52e-01 3.483987405e+03 3.370996410e+03 2.1e-03 0.34
13 3.4e+01 2.5e-02 3.9e+00 7.54e-01 2.857108876e+03 2.753936178e+03 1.8e-03 0.34
14 2.3e+01 1.7e-02 2.3e+00 8.26e-01 1.161615029e+03 1.089238797e+03 1.2e-03 0.36
15 1.0e+01 7.5e-03 6.9e-01 8.21e-01 -1.388036570e+03 -1.421298927e+03 5.3e-04 0.36
16 2.1e+00 1.5e-03 8.7e-02 7.61e-01 -3.325003548e+03 -3.332924471e+03 1.1e-04 0.38
17 4.6e-01 3.5e-04 1.5e-02 4.66e-01 -4.246996265e+03 -4.249474169e+03 2.5e-05 0.38
18 1.1e-01 7.8e-05 3.4e-03 2.60e-01 -4.950037627e+03 -4.950871458e+03 5.6e-06 0.39
19 3.4e-02 2.5e-05 8.4e-04 5.76e-01 -5.279077280e+03 -5.279357383e+03 1.8e-06 0.39
20 1.3e-02 9.6e-06 4.6e-04 -1.35e-01 -5.778482571e+03 -5.778466139e+03 6.8e-07 0.41
21 3.2e-03 2.4e-06 5.9e-05 5.61e-01 -6.126054300e+03 -6.126065380e+03 1.7e-07 0.41
22 9.2e-04 6.9e-07 2.5e-05 -8.25e-02 -6.707002912e+03 -6.706813014e+03 4.9e-08 0.42
23 2.0e-04 1.5e-07 3.6e-06 4.02e-01 -7.055402562e+03 -7.055291098e+03 1.0e-08 0.42
24 4.7e-05 3.5e-08 1.3e-06 -7.73e-02 -7.670937919e+03 -7.670643920e+03 2.5e-09 0.44
25 1.2e-05 8.8e-09 2.2e-07 4.93e-01 -7.962614624e+03 -7.962474362e+03 6.3e-10 0.45
26 3.3e-06 2.4e-09 9.2e-08 -1.03e-01 -8.557706069e+03 -8.557364850e+03 1.7e-10 0.47
27 7.6e-07 5.6e-10 1.3e-08 5.12e-01 -8.860031035e+03 -8.859896737e+03 4.0e-11 0.47
28 2.2e-07 1.7e-10 5.8e-09 -4.66e-02 -9.409450749e+03 -9.409150389e+03 1.2e-11 0.48
29 5.1e-08 3.8e-11 9.0e-10 4.80e-01 -9.708652279e+03 -9.708520019e+03 2.7e-12 0.48
30 1.5e-08 1.1e-11 3.7e-10 -1.77e-02 -1.019230826e+04 -1.019205073e+04 8.1e-13 0.50
31 3.5e-09 2.6e-12 6.3e-11 3.59e-01 -1.050469924e+04 -1.050455435e+04 1.8e-13 0.52
32 1.2e-09 9.2e-13 2.8e-11 -1.18e-02 -1.084393066e+04 -1.084370338e+04 6.6e-14 0.52
33 3.7e-10 2.8e-13 7.1e-12 2.55e-01 -1.111236923e+04 -1.111221037e+04 2.0e-14 0.53
34 1.4e-10 1.0e-13 2.6e-12 2.09e-01 -1.131935672e+04 -1.131920892e+04 7.5e-15 0.53
35 5.4e-11 4.0e-14 9.2e-13 2.43e-01 -1.149159883e+04 -1.149147149e+04 2.9e-15 0.55
36 1.9e-11 1.4e-14 2.7e-13 3.74e-01 -1.162771519e+04 -1.162762861e+04 1.0e-15 0.56
37 1.9e-11 1.4e-14 2.7e-13 4.82e-01 -1.162771519e+04 -1.162762861e+04 1.0e-15 0.56
38 1.9e-11 1.4e-14 2.7e-13 6.56e-01 -1.162771519e+04 -1.162762861e+04 1.0e-15 0.58
Optimizer terminated. Time: 0.61

Interior-point solution summary
Problem status : PRIMAL_AND_DUAL_FEASIBLE
Solution status : OPTIMAL
Primal. obj: -1.1627715193e+04 nrm: 8e+07 Viol. con: 2e-04 var: 0e+00 cones: 0e+00
Dual. obj: -1.1627628612e+04 nrm: 2e+01 Viol. con: 0e+00 var: 1e-07 cones: 0e+00
Optimizer summary
Optimizer - time: 0.61
Interior-point - iterations : 39 time: 0.58
Basis identification - time: 0.00
Primal - iterations : 0 time: 0.00
Dual - iterations : 0 time: 0.00
Clean primal - iterations : 0 time: 0.00
Clean dual - iterations : 0 time: 0.00
Simplex - time: 0.00
Primal simplex - iterations : 0 time: 0.00
Dual simplex - iterations : 0 time: 0.00
Mixed integer - relaxations: 0 time: 0.00


Status: Solved
Optimal value (cvx_optval): +483.219

Mosek solves you problem nicely.

How do you conclude something is wrong?

Thank you for your kindly reply.
Yes, Mosek seems to solve it well. I set a variable named sum_r4 to calculate the objective function with optimal solution X and Y. It’s not equal to cvx_optval.
For example, I run code for another time and I get this results.

My guess is that this is a bug in CVX. sum_r4 is calculated only with MATLAB data and CVX variables, with no CVX expressions; so it should match cvx_optval. I suggest you file a bug report. When you do so, I suggest you eliminate the while loop, so that there is just one invocation of Mosek. The discrepancy manifests itself on the first such problem.

I also duplicated the apparent bug using SeDuMi with CVX’s Successive Approximation method.

Of course, random numbers are being generated, so each time it is run, if the random numbers are not controlled, However, each time I observed a discrepancy.

Maybe you can fix the seed for the random number generator.

Yes, that is a goiod idea for the bug report. But the bug seems to occur regardless of the exact random data.

I can see cvx dualizes the problem. It could be the bug is in the dualizer so if you can turn that feature off it may serve as a work around.

I don’t think there is user control over dualization in CVX. Probably only the developer @mcg could do that.

Thank you for your help. I will eliminate the while loop and file a bug report.

I also tried SeDuMi and SDPT3, they both have this problem.

However, I don’t think random numbers are a problem because the random numbers remain the same when the while-loop is executed. This problem occurs each time I run Matlab code.

Thank you for your help. I will fix the seed when I file the bug report.

Hi, Mark.

Today I try to use three solvers Mosek, SeDuMi and SDPT3 to compute the objective function with the obtained CVX optimal value after CVX execution (under the same values of variables and eliminate the for-while loop). It turns out that there are different results for different solvers! Here are the output of the objective function with obtained optimal values.

So I was thinking whether the objective function is correct. For example, I use ‘shiftdim’ and ‘repmat’ operation to CVX variables X and Y. X and Y are matrices. Are ‘shiftdim’ and ‘repmat’ operation to CVX variables correct?

You can try rewriting your program without these and see what happens.

I think repmat is supported.by CVX. I don;t know about shiftdim.

I also don;t know about the different solutions from the different solvers. Did you run these with the same inputs, i.e., the same random numbers for each solver?

Yeah, I wrote a simple program without repmat and shiftdim. The optimal values and cvx_optval obtained from the program without repmat and shiftdim are equal to those obtained from the program with repmat and shiftdim. So I think there is no problem using repmat and shiftdim.

I run the same cvx code under the same random numbers. And the results from different solvers were not the same.

Maybe it’s not a bug. I think I should check my model again. Thank you for your help.

Can you figure out which of repmat and shiftdim is causing the problem?

I think both are not the reason.

Since squeeze is another function confused me, I use repmat and squeeze in the first program. I use elements operation to represent the objective function in the second program. These two programs return the same results. Shiftdim can be validated in the same way.

n=2;
cvx_begin
cvx_solver mosek
variables x(n,n) y(n,n)
minimize(-sum(sum(log(squeeze(sum(repmat(x,[1,1,n]),1)))+log(y))))
subject to
sum(x,1)<=1
sum(x,2)==1
sum(y,1)<=1
sum(y,2)==1
cvx_end

n=2;
cvx_begin
cvx_solver mosek
variables x1(n,n) y1(n,n)
minimize(-sum(sum(log([x1(1,1)+x1(2,1),x1(1,1)+x1(2,1);x1(1,2)+x1(2,2),x1(1,2)+x1(2,2)])+log(y1))))
subject to
sum(x1,1)<=1
sum(x1,2)==1
sum(y1,1)<=1
sum(y1,2)==1
cvx_end

Hello, I’m having the same problem, did you solve it??

@kwssh You are not having the same problem as in this thread. Your problem has CVX expressions in the objective function, whereas the objective function in this topic only involves CVX variables. My answers in your other thread address the phenomenon you are actually encountering.