[37] | 1 | function output = callsedumi(interfacedata) |
---|
| 2 | |
---|
| 3 | % Author Johan Löfberg |
---|
| 4 | % $Id: callsedumi.m,v 1.26 2006/08/10 18:00:19 joloef Exp $ |
---|
| 5 | |
---|
| 6 | % Retrieve needed data |
---|
| 7 | options = interfacedata.options; |
---|
| 8 | F_struc = interfacedata.F_struc; |
---|
| 9 | c = interfacedata.c; |
---|
| 10 | K = interfacedata.K; |
---|
| 11 | ub = interfacedata.ub; |
---|
| 12 | lb = interfacedata.lb; |
---|
| 13 | |
---|
| 14 | % Create the parameter structure |
---|
| 15 | pars = options.sedumi; |
---|
| 16 | pars.fid = double(options.verbose); |
---|
| 17 | |
---|
| 18 | % ********************************************* |
---|
| 19 | % Bounded variables converted to constraints |
---|
| 20 | % N.B. Only happens when caller is BNB |
---|
| 21 | % ********************************************* |
---|
| 22 | if ~isempty(ub) |
---|
| 23 | [F_struc,K] = addbounds(F_struc,K,ub,lb); |
---|
| 24 | end |
---|
| 25 | |
---|
| 26 | % Avoid bug (by design?) in SeDuMi on 1D second order cones |
---|
| 27 | if any(K.q == 2) |
---|
| 28 | [F_struc,K] = fix1Dqcone(F_struc,K); |
---|
| 29 | end |
---|
| 30 | |
---|
| 31 | if options.savedebug |
---|
| 32 | save sedumidebug F_struc c K pars |
---|
| 33 | end |
---|
| 34 | |
---|
| 35 | % ********************************************* |
---|
| 36 | % Call SeDuMi |
---|
| 37 | % ********************************************* |
---|
| 38 | if options.showprogress;showprogress(['Calling ' interfacedata.solver.tag],options.showprogress);end |
---|
| 39 | |
---|
| 40 | solvertime = clock; |
---|
| 41 | problem = 0; |
---|
| 42 | try |
---|
| 43 | [x_s,y_s,info] = sedumi(-F_struc(:,2:end),-c,F_struc(:,1),K,pars); |
---|
| 44 | catch |
---|
| 45 | try |
---|
| 46 | if options.verbose > 0 |
---|
| 47 | disp(' '); |
---|
| 48 | disp('SeDuMi had unexplained problems, probably due to linear dependence.') |
---|
| 49 | disp('YALMIP tweaks the problem and restarts...') |
---|
| 50 | disp(' '); |
---|
| 51 | end |
---|
| 52 | % Boring issue in sedumi for trivial problem min x+y, s.t x+y>0 |
---|
| 53 | n = length(c); |
---|
| 54 | [F_struc,K] = addbounds(F_struc,K,ones(n,1)*1e6,-ones(n,1)*1e6); |
---|
| 55 | [x_s,y_s,info] = sedumi(-F_struc(:,2:end),-c,F_struc(:,1),K,pars); |
---|
| 56 | x_s((1:2*n)+K.f)=[]; |
---|
| 57 | K.l=K.l-2*n; |
---|
| 58 | catch |
---|
| 59 | disp('Unexplained crash in SeDuMi! (could be memory issues)') |
---|
| 60 | disp('If you have SDPT3 3.02 on you path, remove it.') |
---|
| 61 | disp('If this doesn''t work, make sure you have a recent and compiled version') |
---|
| 62 | end |
---|
| 63 | end |
---|
| 64 | if interfacedata.getsolvertime solvertime = etime(clock,solvertime);else solvertime = 0;end |
---|
| 65 | |
---|
| 66 | |
---|
| 67 | % Internal format |
---|
| 68 | Primal = y_s; |
---|
| 69 | Dual = x_s; |
---|
| 70 | |
---|
| 71 | temp = info.pinf; |
---|
| 72 | pinf = info.dinf; |
---|
| 73 | dinf = temp; |
---|
| 74 | |
---|
| 75 | % Check for reported errors |
---|
| 76 | if (pinf==0) & (dinf==0) |
---|
| 77 | problem = 0; % No problems |
---|
| 78 | end |
---|
| 79 | |
---|
| 80 | % We can only report one error, use priorities |
---|
| 81 | if (problem==0) & (pinf==1) |
---|
| 82 | problem = 1; % Primal infeasability |
---|
| 83 | end |
---|
| 84 | |
---|
| 85 | if (problem==0) & (dinf==1) |
---|
| 86 | problem = 2; % Dual infeasability |
---|
| 87 | end |
---|
| 88 | |
---|
| 89 | if (problem==0) & (info.numerr==1) | (info.numerr==2) |
---|
| 90 | problem = 4; %Numerical problems |
---|
| 91 | end |
---|
| 92 | |
---|
| 93 | if (problem==0) & (info.iter >= options.sedumi.maxiter) |
---|
| 94 | % Did we need exactly maxiter iterations to find optimum |
---|
| 95 | if (pinf==0) & (dinf==0) & (info.numerr==0) |
---|
| 96 | problem = 0; % Yes |
---|
| 97 | else |
---|
| 98 | problem = 3; % No, we are not optimal yet |
---|
| 99 | end |
---|
| 100 | end |
---|
| 101 | |
---|
| 102 | if (problem==0) & (info.feasratio<0.98) |
---|
| 103 | problem = 4; |
---|
| 104 | end |
---|
| 105 | |
---|
| 106 | % Fix for cases not really explained in documentation of sedumi? |
---|
| 107 | if (abs(info.feasratio+1)<0.1) & (pinf==0) & (dinf==0) |
---|
| 108 | problem = 1; |
---|
| 109 | end |
---|
| 110 | if (abs(info.feasratio+1)<0.1) & (pinf==0) & (dinf==0) & (c'*y_s<-1e10) |
---|
| 111 | problem = 2; |
---|
| 112 | end |
---|
| 113 | |
---|
| 114 | |
---|
| 115 | infostr = yalmiperror(problem,interfacedata.solver.tag); |
---|
| 116 | |
---|
| 117 | % Save ALL data sent to solver |
---|
| 118 | if options.savesolverinput |
---|
| 119 | solverinput.A = -F_struc(:,2:end); |
---|
| 120 | solverinput.c = F_struc(:,1); |
---|
| 121 | solverinput.b = -c; |
---|
| 122 | solverinput.K = K; |
---|
| 123 | solverinput.pars = pars; |
---|
| 124 | else |
---|
| 125 | solverinput = []; |
---|
| 126 | end |
---|
| 127 | |
---|
| 128 | % Save ALL data from the solution? |
---|
| 129 | if options.savesolveroutput |
---|
| 130 | solveroutput.x = x_s; |
---|
| 131 | solveroutput.y = y_s; |
---|
| 132 | solveroutput.info = info; |
---|
| 133 | else |
---|
| 134 | solveroutput = []; |
---|
| 135 | end |
---|
| 136 | |
---|
| 137 | % Standard interface |
---|
| 138 | output.Primal = Primal; |
---|
| 139 | output.Dual = Dual; |
---|
| 140 | output.Slack = []; |
---|
| 141 | output.problem = problem; |
---|
| 142 | output.infostr = infostr; |
---|
| 143 | output.solverinput = solverinput; |
---|
| 144 | output.solveroutput= solveroutput; |
---|
| 145 | output.solvertime = solvertime; |
---|
| 146 | |
---|
| 147 | function [new_F_struc,K] = fix1Dqcone(F_struc,K); |
---|
| 148 | |
---|
| 149 | new_F_struc = F_struc(1:(K.l+K.f),:); |
---|
| 150 | top = K.f + K.l + 1; |
---|
| 151 | for i = 1:length(K.q) |
---|
| 152 | if K.q(i) == 2 |
---|
| 153 | new_F_struc = [new_F_struc;F_struc(top,:);F_struc(top+1,:);F_struc(top,:)*0]; |
---|
| 154 | K.q(i) = 3; |
---|
| 155 | top = top + 2; |
---|
| 156 | else |
---|
| 157 | new_F_struc = [new_F_struc;F_struc(top:top+K.q(i),:);F_struc(top+1,:);F_struc(top,:)*0]; |
---|
| 158 | top = top + K.q(i); |
---|
| 159 | end |
---|
| 160 | end |
---|
| 161 | new_F_struc = [new_F_struc;F_struc(top:end,:)]; |
---|