65 lines
1.9 KiB
Mathematica
65 lines
1.9 KiB
Mathematica
|
|
function F = nnz_internal(z,x,direction)
|
||
|
|
|
||
|
|
switch direction
|
||
|
|
case 0
|
||
|
|
[nx,mx] = size(x);
|
||
|
|
if issymmetric(x)
|
||
|
|
d = binvar(nx,nx); % d == 1 means x(i,j) can be non-zero
|
||
|
|
else
|
||
|
|
d = binvar(nx,mx,'full');
|
||
|
|
end
|
||
|
|
x = reshape(x,nx*mx,1);
|
||
|
|
d = reshape(d,nx*mx,1);
|
||
|
|
[M,m] = derivebounds(x);
|
||
|
|
F = (m.*d <= x <= M.*d) + (z == sum(sum(d)));
|
||
|
|
F = F + (0 <=z <= nx*mx);
|
||
|
|
|
||
|
|
case 1
|
||
|
|
[nx,mx] = size(x);
|
||
|
|
if issymmetric(x)
|
||
|
|
du = binvar(nx,nx); % du == 1 means x(i,j) > 0
|
||
|
|
dd = binvar(nx,nx); % dd == 1 means x(i,j) < 0
|
||
|
|
else
|
||
|
|
du = binvar(nx,mx,'full');
|
||
|
|
dd = binvar(nx,mx,'full');
|
||
|
|
end
|
||
|
|
x = reshape(x,nx*mx,1);
|
||
|
|
du = reshape(du,nx*mx,1);
|
||
|
|
dd = reshape(dd,nx*mx,1);
|
||
|
|
[M,m] = derivebounds(x);
|
||
|
|
fixedzeros = find(M==m & m==0);
|
||
|
|
positive = find(m>0);
|
||
|
|
negative = find(M<0);
|
||
|
|
left = setdiff(1:nx*mx,[fixedzeros;positive;negative]);
|
||
|
|
|
||
|
|
m = m(left);
|
||
|
|
M = M(left);
|
||
|
|
x = x(left);
|
||
|
|
du = du(left);
|
||
|
|
dd = dd(left);
|
||
|
|
du(M<=0) = 0;
|
||
|
|
dd(m>=0) = 0;
|
||
|
|
F = [];
|
||
|
|
eps=1e-3;
|
||
|
|
F = F + (sum([du dd],2) <= 1);
|
||
|
|
F = F + (z == length(negative)+length(positive) + ((sum(du) + sum(dd))));
|
||
|
|
F = F + (x >= eps+(m-eps).*(1-du));
|
||
|
|
F = F + (x <= eps+(M-eps).*du);
|
||
|
|
F = F + (x <=-eps+(M+eps).*(1-dd));
|
||
|
|
F = F + (x >= -eps+(m+eps).*dd);
|
||
|
|
F = F + (m.*(du+dd) <= x <= M.*(dd+du));
|
||
|
|
F = F + (0 <= z <=nx*mx);
|
||
|
|
|
||
|
|
%F = F + (x > 0+(m-0).*(1-du));
|
||
|
|
% F = F + (x < -0+(0+M).*(1-dd));
|
||
|
|
%F = F + (0 <= z <=nx*mx);
|
||
|
|
|
||
|
|
% F = (m.*(du+dd) <= x <= M.*(du+dd)) + (sum([du dd],2) <= 1);
|
||
|
|
% F = F + (z == ((sum(du) + sum(dd))));
|
||
|
|
% F = F + (x > 1e-5+(-1+m).*(1-du));
|
||
|
|
% F = F + (x < -1e-5+(1+M).*(1-dd));
|
||
|
|
% F = F + (0 <= z <=nx*mx);
|
||
|
|
otherwise
|
||
|
|
end
|
||
|
|
|