112 lines
2.6 KiB
Matlab
Executable File
112 lines
2.6 KiB
Matlab
Executable File
function [lb,ub,redundant,psstruct,infeasible] = tightenbounds(A,b,lb,ub,integer_variables,binary_variables,changed_bounds);
|
|
%TIGHTENBOUNDS Internal function to perform bound tightening
|
|
|
|
% Author Johan Löfberg
|
|
% $Id: tightenbounds.m,v 1.1 2006-03-30 13:56:54 joloef Exp $
|
|
|
|
% Simple bound pre-processing (paper by Savelsbergh)
|
|
% No code optimization at all
|
|
|
|
if nargin < 5
|
|
integer_variables = [];
|
|
end
|
|
if nargin < 6
|
|
binary_variables = [];
|
|
end
|
|
if nargin < 7
|
|
changed_bounds = [];
|
|
end
|
|
|
|
ubnew = ub;
|
|
lbnew = lb;
|
|
goon = 1;
|
|
|
|
AL0A = (A>0).*A;
|
|
AG0A = (A<0).*A;
|
|
|
|
At = A';
|
|
use_indicies=ones(length(b),1);
|
|
used = full(any(A(:,find(changed_bounds)),2));
|
|
isbinary = ismembcYALMIP(1:length(lb),binary_variables);
|
|
isinteger = ismembcYALMIP(1:length(lb),binary_variables);
|
|
|
|
goon = all(lb<=ub);
|
|
infeasible = ~goon;
|
|
Cpp = cell(1,size(At,2));
|
|
Cmm = cell(1,size(At,2));
|
|
r1 = cell(1,size(At,2));
|
|
for i = 1:size(At,2)
|
|
[ii,jj,kk] = find(At(:,i));
|
|
Cpp{i} = ii(kk>0);
|
|
Cmm{i} = ii(kk<0);
|
|
end
|
|
|
|
iter1 = 1;
|
|
if ~infeasible & (iter1 < 10)
|
|
iter2 = 1;
|
|
while goon & iter2 < 10
|
|
|
|
bi_up = AL0A*ub+AG0A*lb;
|
|
bi_dn = AL0A*lb+AG0A*ub;
|
|
%
|
|
if ~isempty(find(bi_dn>b))
|
|
infeasible = 1;
|
|
break;
|
|
end
|
|
%
|
|
bminusbdn=b-bi_dn;
|
|
for i = find(use_indicies & used)'
|
|
|
|
|
|
Cp = Cpp{i};
|
|
if ~isempty(Cp)
|
|
r = At(Cp,i);
|
|
new1=lbnew(Cp)+bminusbdn(i)./r;
|
|
ubnew(Cp) = min(ubnew(Cp),new1);
|
|
end
|
|
|
|
Cm = Cmm{i};
|
|
if ~isempty(Cm)
|
|
r = At(Cm,i);
|
|
new2=ubnew(Cm)+bminusbdn(i)./r;
|
|
lbnew(Cm) = max(lbnew(Cm),new2);
|
|
end
|
|
|
|
if any(lbnew>ubnew)
|
|
infeasible = 1;
|
|
break
|
|
end
|
|
end
|
|
|
|
if ~infeasible
|
|
|
|
lbnew(integer_variables) = round(lbnew(integer_variables)+0.49999);
|
|
ubnew(integer_variables) = round(ubnew(integer_variables)-0.49999);
|
|
|
|
lbnew(binary_variables) = round(lbnew(binary_variables)+0.49999);
|
|
ubnew(binary_variables) = round(ubnew(binary_variables)-0.49999);
|
|
|
|
goon = (~all((lb==lbnew) & (ub==ubnew))) & all(lbnew<=ubnew);
|
|
|
|
used = (lb~=lbnew) | (ub~=ubnew);
|
|
used = full(any(A(:,find(used)),2));
|
|
|
|
lb = lbnew;
|
|
ub = ubnew;
|
|
|
|
use_indicies = use_indicies & bi_up>b;
|
|
else
|
|
goon = 0;
|
|
end
|
|
iter2 = iter2 + 1;
|
|
end
|
|
iter1 = iter1 + 1;
|
|
redundant = find(bi_up<=b-0.001);
|
|
else
|
|
redundant=[];
|
|
end
|
|
psstruct.AL0A = AL0A;
|
|
psstruct.AG0A = AG0A;
|
|
|
|
|