SCIP-SDP  2.1.0
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
sdpi.c
Go to the documentation of this file.
1 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
2 /* */
3 /* This file is part of SCIPSDP - a solving framework for mixed-integer */
4 /* semidefinite programms based on SCIP. */
5 /* */
6 /* Copyright (C) 2011-2013 Discrete Optimization, TU Darmstadt */
7 /* EDOM, FAU Erlangen-Nürnberg */
8 /* 2014-2016 Discrete Optimization, TU Darmstadt */
9 /* */
10 /* */
11 /* This program is free software; you can redistribute it and/or */
12 /* modify it under the terms of the GNU Lesser General Public License */
13 /* as published by the Free Software Foundation; either version 3 */
14 /* of the License, or (at your option) any later version. */
15 /* */
16 /* This program is distributed in the hope that it will be useful, */
17 /* but WITHOUT ANY WARRANTY; without even the implied warranty of */
18 /* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the */
19 /* GNU Lesser General Public License for more details. */
20 /* */
21 /* You should have received a copy of the GNU Lesser General Public License */
22 /* along with this program; if not, write to the Free Software */
23 /* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA.*/
24 /* */
25 /* */
26 /* Based on SCIP - Solving Constraint Integer Programs */
27 /* Copyright (C) 2002-2016 Zuse Institute Berlin */
28 /* SCIP is distributed under the terms of the SCIP Academic Licence, */
29 /* see file COPYING in the SCIP distribution. */
30 /* */
31 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
32 
33 /* #define SCIP_DEBUG*/
34 /* #define SCIP_MORE_DEBUG*/
35 
40 #include <assert.h>
41 #include <time.h>
42 
43 #include "sdpi/sdpisolver.h"
44 #include "sdpi/sdpi.h"
45 #include "scipsdp/SdpVarfixer.h"
46 #include "sdpi/lapack.h" /* to check feasibility if all variables are fixed during preprocessing */
47 
48 #include "blockmemshell/memory.h" /* for memory allocation */
49 #include "scip/def.h" /* for SCIP_Real, _Bool, ... */
50 #include "scip/pub_misc.h" /* for sorting */
51 
52 /* turn off lint warnings for whole file: */
53 /*lint --e{788,818}*/
54 
55 
57 #define BMS_CALL(x) do \
58  { \
59  if( NULL == (x) ) \
60  { \
61  SCIPerrorMessage("No memory in function call\n"); \
62  return SCIP_NOMEMORY; \
63  } \
64  } \
65  while( FALSE )
66 
68 #define CHECK_IF_SOLVED(sdpi) do \
69  { \
70  if ( ! (sdpi->solved) ) \
71  { \
72  SCIPerrorMessage("Tried to access solution information ahead of solving! \n"); \
73  return SCIP_LPERROR; \
74  } \
75  } \
76  while( FALSE )
77 
79 #define CHECK_IF_SOLVED_BOOL(sdpi) do \
80  { \
81  if ( ! (sdpi->solved) ) \
82  { \
83  SCIPerrorMessage("Tried to access solution information ahead of solving! \n"); \
84  return FALSE; \
85  } \
86  } \
87  while( FALSE )
88 
90 #define DUPLICATE_ARRAY_NULL(blkmem, target, source, size) do \
91  { \
92  if (size > 0) \
93  BMS_CALL( BMSduplicateBlockMemoryArray(blkmem, target, source, size) ); \
94  else \
95  *target = NULL; \
96  } \
97  while( FALSE )
98 
100 #define SCIP_CALL_PARAM(x) do \
101  { \
102  SCIP_RETCODE _restat_; \
103  if ( (_restat_ = (x)) != SCIP_OKAY ) \
104  { \
105  if ( _restat_ != SCIP_PARAMETERUNKNOWN ) \
106  { \
107  SCIPerrorMessage("Error <%d> in function call\n", _restat_); \
108  SCIPABORT(); \
109  } \
110  return _restat_; \
111  } \
112  } \
113  while( FALSE )
114 
115 /* #define PRINTSLATER */
116 #define NINCREASESGAMMA 2
117 #define MIN_EPSILON 1e-10
119 #define DEFAULT_SDPSOLVEREPSILON 1e-4
120 #define DEFAULT_SDPSOLVERFEASTOL 1e-6
121 #define DEFAULT_PENALTYPARAM 1e+5
122 #define DEFAULT_MAXPENALTYPARAM 1e+10
125 struct SCIP_SDPi
126 {
127  SCIP_SDPISOLVER* sdpisolver;
128  SCIP_MESSAGEHDLR* messagehdlr;
129  BMS_BLKMEM* blkmem;
130  int nvars;
131  SCIP_Real* obj;
132  SCIP_Real* lb;
133  SCIP_Real* ub;
134  int nsdpblocks;
135  int* sdpblocksizes;
136  int* sdpnblockvars;
138  /* constant SDP data: */
139  int sdpconstnnonz;
140  int* sdpconstnblocknonz;
142  int** sdpconstrow;
143  int** sdpconstcol;
144  SCIP_Real** sdpconstval;
146  /* non-constant SDP data: */
147  int sdpnnonz;
148  int** sdpnblockvarnonz;
150  int** sdpvar;
152  int*** sdprow;
154  int*** sdpcol;
155  SCIP_Real*** sdpval;
157  /* lp data: */
158  int nlpcons;
159  SCIP_Real* lplhs;
160  SCIP_Real* lprhs;
161  int lpnnonz;
162  int* lprow;
163  int* lpcol;
164  SCIP_Real* lpval;
166  /* other data */
167  int slatercheck;
168  int sdpid;
169  int niterations;
170  int nsdpcalls;
171  SCIP_Bool solved;
172  SCIP_Bool penalty;
173  SCIP_Bool infeasible;
174  SCIP_Bool allfixed;
175  SCIP_Real epsilon;
176  SCIP_Real feastol;
177  SCIP_Real penaltyparam;
178  SCIP_Real maxpenaltyparam;
179  SCIP_Real bestbound;
180  SCIP_SDPSLATER primalslater;
181  SCIP_SDPSLATER dualslater;
182 };
183 
184 /*
185  * Local Functions
186  */
187 
192 static
194  int* i,
195  int* j
196  )
197 {
198  if ( *i < *j )
199  {
200  int temp;
201  temp = *i;
202  *i = *j;
203  *j = temp;
204  }
205 }
206 
207 #ifndef NDEBUG
208 
209 static
210 SCIP_Bool isFixed(
211  SCIP_SDPI* sdpi,
212  int v
213  )
214 {
215  SCIP_Real lb;
216  SCIP_Real ub;
217 
218  assert ( sdpi != NULL );
219  assert ( v < sdpi->nvars );
220  assert ( sdpi->lb != NULL );
221  assert ( sdpi->ub != NULL );
222 
223  lb = sdpi->lb[v];
224  ub = sdpi->ub[v];
225 
226  assert( lb < ub + sdpi->feastol || sdpi->infeasible );
227 
228  return ( REALABS(ub-lb) <= sdpi->feastol );
229 }
230 #else
231 #define isFixed(sdpi, v) (REALABS(sdpi->ub[v] - sdpi->lb[v]) <= sdpi->feastol)
232 #endif
233 
241 static
243  SCIP_SDPI* sdpi,
244  int* sdpconstnnonz,
245  int* sdpconstnblocknonz,
247  int** sdpconstrow,
248  int** sdpconstcol,
249  SCIP_Real** sdpconstval
250  )
251 {
252  int i;
253  int v;
254  int block;
255  int* nfixednonz;
256  int** fixedrows;
257  int** fixedcols;
258  SCIP_Real** fixedvals;
259 
260  assert ( sdpi != NULL );
261  assert ( sdpconstnnonz != NULL );
262  assert ( sdpconstnblocknonz != NULL );
263  assert ( sdpconstrow != NULL );
264  assert ( sdpconstcol != NULL );
265  assert ( sdpconstval != NULL );
266 #ifndef NDEBUG
267  for (block = 0; block < sdpi->nsdpblocks; block++)
268  {
269  assert ( sdpconstrow[block] != NULL );
270  assert ( sdpconstcol[block] != NULL );
271  assert ( sdpconstval[block] != NULL );
272  }
273 #endif
274 
275  fixedrows = NULL;
276  fixedcols = NULL;
277  fixedvals = NULL;
278 
279  /* allocate memory for the nonzeros that need to be fixed, as this is only temporarly needed, we allocate as much as theoretically possible */
280  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &nfixednonz, sdpi->nsdpblocks) );
281  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &fixedrows, sdpi->nsdpblocks) );
282  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &fixedcols, sdpi->nsdpblocks) );
283  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &fixedvals, sdpi->nsdpblocks) );
284 
285  for (block = 0; block < sdpi->nsdpblocks; block++)
286  {
287  /* compute the number of fixed nonzeros in this block */
288  nfixednonz[block] = 0;
289  for (v = 0; v < sdpi->sdpnblockvars[block]; v++)
290  {
291  if (isFixed(sdpi, sdpi->sdpvar[block][v]))
292  nfixednonz[block] += sdpi->sdpnblockvarnonz[block][v];
293  }
294 
295  fixedrows[block] = NULL;
296  fixedcols[block] = NULL;
297  fixedvals[block] = NULL;
298 
299  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &(fixedrows[block]), nfixednonz[block]) );
300  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &(fixedcols[block]), nfixednonz[block]) );
301  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &(fixedvals[block]), nfixednonz[block]) );
302 
303  /* set nfixednonz to 0 to use it for indexing later (at the end of the next for-block it will again have the same value) */
304  nfixednonz[block] = 0;
305  }
306 
307  /* iterate over all variables, saving the nonzeros of the fixed ones */
308  for (block = 0; block < sdpi->nsdpblocks; block++)
309  {
310  for (v = 0; v < sdpi->sdpnblockvars[block]; v++)
311  {
312  if (isFixed(sdpi, sdpi->sdpvar[block][v]))
313  {
314  for (i = 0; i < sdpi->sdpnblockvarnonz[block][v]; i++)
315  {
316  fixedrows[block][nfixednonz[block]] = sdpi->sdprow[block][v][i];
317  fixedcols[block][nfixednonz[block]] = sdpi->sdpcol[block][v][i];
318  /* this is the final value to add, so we no longer have to remember, from which variable this nonzero comes,
319  * the -1 comes from +y_iA_i but -A_0 */
320  fixedvals[block][nfixednonz[block]] = - sdpi->sdpval[block][v][i] * sdpi->lb[sdpi->sdpvar[block][v]];
321  nfixednonz[block]++;
322  }
323  }
324  }
325  }
326 
327  /* compute the constant matrix */
328  *sdpconstnnonz = 0;
329  for (block = 0; block < sdpi->nsdpblocks; block++)
330  {
331  SCIP_CALL( SCIPsdpVarfixerMergeArraysIntoNew(sdpi->blkmem, sdpi->feastol, sdpi->sdpconstrow[block], sdpi->sdpconstcol[block], sdpi->sdpconstval[block],
332  sdpi->sdpconstnblocknonz[block], fixedrows[block], fixedcols[block], fixedvals[block], nfixednonz[block],
333  sdpconstrow[block], sdpconstcol[block], sdpconstval[block], &sdpconstnblocknonz[block]) );
334  *sdpconstnnonz += sdpconstnblocknonz[block];
335  }
336 
337  /* free all memory */
338  for (block = 0; block < sdpi->nsdpblocks; block++)
339  {
340  BMSfreeBlockMemoryArrayNull(sdpi->blkmem, &(fixedvals[block]), nfixednonz[block]);
341  BMSfreeBlockMemoryArrayNull(sdpi->blkmem, &(fixedcols[block]), nfixednonz[block]);
342  BMSfreeBlockMemoryArrayNull(sdpi->blkmem, &(fixedrows[block]), nfixednonz[block]);
343  }
344  BMSfreeBlockMemoryArrayNull(sdpi->blkmem, &fixedvals, sdpi->nsdpblocks);
345  BMSfreeBlockMemoryArrayNull(sdpi->blkmem, &fixedcols, sdpi->nsdpblocks);
346  BMSfreeBlockMemoryArrayNull(sdpi->blkmem, &fixedrows, sdpi->nsdpblocks);
347  BMSfreeBlockMemoryArrayNull(sdpi->blkmem, &nfixednonz, sdpi->nsdpblocks);
348 
349  return SCIP_OKAY;
350 }
351 
355 static
356 SCIP_RETCODE findEmptyRowColsSDP(
357  SCIP_SDPI* sdpi,
358  int* sdpconstnblocknonz,
360  int** sdpconstrow,
361  int** sdpconstcol,
362  SCIP_Real** sdpconstval,
363  int** indchanges,
367  int* nremovedinds,
368  int* blockindchanges,
369  int* nremovedblocks
370  )
371 {
372  int block;
373  int v;
374  int i;
375  int nfoundinds;
376 
377  assert( sdpi != NULL );
378  assert( sdpconstnblocknonz != NULL );
379  assert( sdpconstrow != NULL );
380  assert( sdpconstcol != NULL );
381  assert( sdpconstval != NULL );
382  assert( indchanges != NULL );
383  assert( nremovedinds != NULL );
384  assert( blockindchanges != NULL );
385  assert( nremovedblocks != NULL );
386 
387  /* initialize indchanges with -1 */
388  for (block = 0; block < sdpi->nsdpblocks; block++)
389  {
390  for (i = 0; i < sdpi->sdpblocksizes[block]; i++)
391  indchanges[block][i] = -1;
392  }
393  *nremovedblocks = 0;
394 
395  /* iterate over all active nonzeros, setting the values of indchange for their row and col to 1 (this is an intermediate value to save that the
396  * index is still needed, it will later be set to the number of rows/cols deleted earlier) */
397  for (block = 0; block < sdpi->nsdpblocks; block++)
398  {
399  /* the number of indices already found in this block, saved for prematurely stopping the loops */
400  nfoundinds = 0;
401  for (v = 0; v < sdpi->sdpnblockvars[block]; v++)
402  {
403  if ( ! (isFixed(sdpi, sdpi->sdpvar[block][v])) )
404  {
405  for (i = 0; i < sdpi->sdpnblockvarnonz[block][v]; i++)
406  {
407  assert ( REALABS(sdpi->sdpval[block][v][i]) > sdpi->feastol); /* this should really be a nonzero */
408  if ( indchanges[block][sdpi->sdprow[block][v][i]] == -1 )
409  {
410  indchanges[block][sdpi->sdprow[block][v][i]] = 1;
411  nfoundinds++;
412  }
413  if ( indchanges[block][sdpi->sdpcol[block][v][i]] == -1 )
414  {
415  indchanges[block][sdpi->sdpcol[block][v][i]] = 1;
416  nfoundinds++;
417  }
418  if ( nfoundinds == sdpi->sdpblocksizes[block] )
419  break; /* we're done for this block */
420  }
421  }
422  if (nfoundinds == sdpi->sdpblocksizes[block])
423  break; /* we're done for this block */
424  }
425 
426  if ( nfoundinds < sdpi->sdpblocksizes[block] )
427  {
428  /* if some indices haven't been found yet, look in the constant part for them */
429  for (i = 0; i < sdpconstnblocknonz[block]; i++)
430  {
431  assert ( REALABS(sdpconstval[block][i]) > sdpi->feastol); /* this should really be a nonzero */
432  if ( indchanges[block][sdpconstrow[block][i]] == -1 )
433  {
434  indchanges[block][sdpconstrow[block][i]] = 1;
435  nfoundinds++;
436  }
437  if ( indchanges[block][sdpconstcol[block][i]] == -1 )
438  {
439  indchanges[block][sdpconstcol[block][i]] = 1;
440  nfoundinds++;
441  }
442  if ( nfoundinds == sdpi->sdpblocksizes[block] )
443  break; /* we're done for this block */
444  }
445  }
446 
447  /* now iterate over all indices to compute the final values of indchanges, all 0 are set to -1, all 1 are changed to the number of -1 before it */
448  nremovedinds[block] = 0;
449  for (i = 0; i < sdpi->sdpblocksizes[block]; i++)
450  {
451  if ( indchanges[block][i] == -1 )
452  {
453  SCIPdebugMessage("empty row and col %d were removed from block %d of SDP %d\n", i, block, sdpi->sdpid);
454  /* this index wasn't found (indchanges was initialized with 0), so it can be removed */
455  nremovedinds[block]++;
456  }
457  else
458  {
459  /* this index has been found, so set the value to the number of removed inds before it */
460  indchanges[block][i] = nremovedinds[block];
461  }
462  }
463 
464  /* check if the block became empty */
465  if ( nremovedinds[block] == sdpi->sdpblocksizes[block] )
466  {
467  SCIPdebugMessage("empty block %d detected in SDP %d, this will be removed", block, sdpi->sdpid);
468  blockindchanges[block] = -1;
469  (*nremovedblocks)++;
470  }
471  else
472  blockindchanges[block] = *nremovedblocks;
473  }
474 
475  return SCIP_OKAY;
476 }
477 
482 static
484  SCIP_SDPI* sdpi,
485  int* nactivelpcons,
486  SCIP_Real* lplhsafterfix,
490  SCIP_Real* lprhsafterfix,
494  int* rownactivevars,
495  SCIP_Bool* fixingsfound
496  )
497 {
498  int i;
499  int c;
500  int lastrow = -1;
501  int nonzind = -1;
502  int nonzcol = -1;
503  SCIP_Real nonzval;
504 
505  assert( sdpi != NULL );
506  assert( nactivelpcons != NULL );
507  assert( sdpi->nlpcons == 0 || lplhsafterfix != NULL );
508  assert( sdpi->nlpcons == 0 || lprhsafterfix != NULL );
509  assert( sdpi->nlpcons == 0 || rownactivevars != NULL );
510  assert( sdpi->nlpcons == 0 || fixingsfound != NULL );
511 
512  /* if there is no LP-part, there is nothing to do */
513  if ( sdpi->nlpcons == 0 || sdpi->lpnnonz == 0 )
514  {
515  *nactivelpcons = 0;
516  return SCIP_OKAY;
517  }
518 
519  /* initialize rownactivevars */
520  for (c = 0; c < sdpi->nlpcons; c++)
521  rownactivevars[c] = 0;
522  *nactivelpcons = 0;
523 
524  for (i = 0; i < sdpi->lpnnonz; i++)
525  {
526  assert( i == 0 || sdpi->lprow[i-1] <= sdpi->lprow[i] );
527 
528  /* we reached a new row */
529  if ( sdpi->lprow[i] > lastrow )
530  {
531  /* if the last row had at least two active variables, we keep the lhs- and rhs-value */
532  if ( lastrow >= 0 && rownactivevars[lastrow] > 1 )
533  (*nactivelpcons)++;
534  else if ( lastrow >= 0 && rownactivevars[lastrow] == 1 )
535  {
536  assert( 0 <= nonzind && nonzind < sdpi->lpnnonz );
537 
538  nonzcol = sdpi->lpcol[nonzind];
539  assert( 0 <= nonzcol && nonzcol < sdpi->nvars );
540 
541  nonzval = sdpi->lpval[nonzind];
542  assert( REALABS(nonzval) > sdpi->feastol );
543 
544  /* we have to check if this is an improvement of the current bound */
545  if ( nonzval < 0.0 ) /* we have to compare with the upper bound for lhs and lower bound for rhs */
546  {
547  /* check for the left-hand-side */
548  if ( (lplhsafterfix[*nactivelpcons] > - SCIPsdpiInfinity(sdpi)) &&
549  ( (lplhsafterfix[*nactivelpcons] / nonzval) < sdpi->ub[nonzcol] - sdpi->feastol) )
550  {
551  /* this bound is sharper than the original one */
552  SCIPdebugMessage("empty LP-row %d has been removed from SDP %d, upper bound of variable %d has been sharpened to %f "
553  "(originally %f)\n", lastrow, sdpi->sdpid, nonzcol, lplhsafterfix[*nactivelpcons] / nonzval, sdpi->ub[nonzcol]);
554  sdpi->ub[nonzcol] = lplhsafterfix[*nactivelpcons] / nonzval;
555 
556  /* check if this leads to a fixing of this variable */
557  if ( REALABS(sdpi->lb[nonzcol] - sdpi->ub[nonzcol]) < sdpi->feastol )
558  {
559  *fixingsfound = TRUE;
560  SCIPdebugMessage("computeLpLhsRhsAfterFixings fixed variable %d to value %f in SDP %d\n",
561  nonzcol, sdpi->lb[nonzcol], sdpi->sdpid);
562  }
563  /* check if this makes the problem infeasible */
564  if (sdpi->ub[nonzcol] < sdpi->lb[nonzcol] - sdpi->feastol)
565  {
566  sdpi->infeasible = TRUE;
567  SCIPdebugMessage("We found an upper bound %f that is lower than the lower bound %f for variable %d, so the problem is infeasible !\n",
568  sdpi->ub[nonzcol], sdpi->lb[nonzcol], nonzcol);
569  return SCIP_OKAY;
570  }
571  }
572  /* check for the right-hand-side */
573  if ( (lprhsafterfix[*nactivelpcons] < SCIPsdpiInfinity(sdpi)) &&
574  ( (lprhsafterfix[*nactivelpcons] / nonzval) > sdpi->lb[nonzcol] + sdpi->feastol) )
575  {
576  /* this bound is sharper than the original one */
577  SCIPdebugMessage("empty LP-row %d has been removed from SDP %d, lower bound of variable %d has been sharpened to %f "
578  "(originally %f)\n", lastrow, sdpi->sdpid, nonzcol, lprhsafterfix[*nactivelpcons] / nonzval, sdpi->lb[nonzcol]);
579  sdpi->lb[nonzcol] = lprhsafterfix[*nactivelpcons] / nonzval;
580 
581  /* check if this leads to a fixing of this variable */
582  if ( REALABS(sdpi->lb[nonzcol] - sdpi->ub[nonzcol]) < sdpi->feastol )
583  {
584  *fixingsfound = TRUE;
585  SCIPdebugMessage("computeLpLhsRhsAfterFixings fixed variable %d to value %f in SDP %d\n",
586  nonzcol, sdpi->lb[nonzcol], sdpi->sdpid);
587  }
588 
589  /* check if this makes the problem infeasible */
590  if (sdpi->ub[nonzcol] < sdpi->lb[nonzcol] - sdpi->feastol)
591  {
592  sdpi->infeasible = TRUE;
593  SCIPdebugMessage("We found an upper bound %f that is lower than the lower bound %f for variable %d, so the problem is infeasible !\n",
594  sdpi->ub[nonzcol], sdpi->lb[nonzcol], nonzcol);
595  return SCIP_OKAY;
596  }
597  }
598  }
599  else /* we compare with the lower bound for lhs and upper bound for rhs */
600  {
601  /* check for the left-hand-side */
602  if ( (lplhsafterfix[*nactivelpcons] < SCIPsdpiInfinity(sdpi)) &&
603  ( (lplhsafterfix[*nactivelpcons] / nonzval) > sdpi->lb[nonzcol] + sdpi->feastol) )
604  {
605  /* this bound is sharper than the original one */
606  SCIPdebugMessage("empty LP-row %d has been removed from SDP %d, lower bound of variable %d has been sharpened to %f "
607  "(originally %f)\n", lastrow, sdpi->sdpid, nonzcol, lplhsafterfix[*nactivelpcons] / nonzval, sdpi->lb[nonzcol]);
608  sdpi->lb[nonzcol] = lplhsafterfix[*nactivelpcons] / nonzval;
609 
610  /* check if this leads to a fixing of this variable */
611  if ( REALABS(sdpi->lb[nonzcol] - sdpi->ub[nonzcol]) < sdpi->feastol )
612  {
613  *fixingsfound = TRUE;
614  SCIPdebugMessage("computeLpLhsRhsAfterFixings fixed variable %d to value %f in SDP %d\n",
615  nonzcol, sdpi->lb[nonzcol], sdpi->sdpid);
616  }
617 
618  /* check if this makes the problem infeasible */
619  if (sdpi->ub[nonzcol] < sdpi->lb[nonzcol] - sdpi->feastol)
620  {
621  sdpi->infeasible = TRUE;
622  SCIPdebugMessage("We found an upper bound %f that is lower than the lower bound %f for variable %d, so the problem is infeasible !\n",
623  sdpi->ub[nonzcol], sdpi->lb[nonzcol], nonzcol);
624  return SCIP_OKAY;
625  }
626  }
627  /* check for the right-hand-side */
628  if ( (lprhsafterfix[*nactivelpcons] > - SCIPsdpiInfinity(sdpi)) &&
629  ( (lprhsafterfix[*nactivelpcons] / nonzval) < sdpi->ub[nonzcol] - sdpi->feastol) )
630  {
631  /* this bound is sharper than the original one */
632  SCIPdebugMessage("empty LP-row %d has been removed from SDP %d, upper bound of variable %d has been sharpened to %f "
633  "(originally %f)\n", lastrow, sdpi->sdpid, nonzcol, lprhsafterfix[*nactivelpcons] / nonzval, sdpi->ub[nonzcol]);
634  sdpi->ub[nonzcol] = lprhsafterfix[*nactivelpcons] / nonzval;
635 
636  /* check if this leads to a fixing of this variable */
637  if ( REALABS(sdpi->lb[nonzcol] - sdpi->ub[nonzcol]) < sdpi->feastol )
638  {
639  *fixingsfound = TRUE;
640  SCIPdebugMessage("computeLpLhsRhsAfterFixings fixed variable %d to value %f in SDP %d\n",
641  nonzcol, sdpi->lb[nonzcol], sdpi->sdpid);
642  }
643 
644  /* check if this makes the problem infeasible */
645  if (sdpi->ub[nonzcol] < sdpi->lb[nonzcol] - sdpi->feastol)
646  {
647  sdpi->infeasible = TRUE;
648  SCIPdebugMessage("We found an upper bound %f that is lower than the lower bound %f for variable %d, so the problem is infeasible !\n",
649  sdpi->ub[nonzcol], sdpi->lb[nonzcol], nonzcol);
650  return SCIP_OKAY;
651  }
652  }
653  }
654  }
655  else if ( lastrow >= 0 ) /* because of earlier ifs we have rownactivevars = 0 */
656  {
657  assert( lastrow == -1 || rownactivevars[lastrow] == 0 );
658  /* we have a constraint lhs <= 0 <= rhs, so lhs should be non-positive and rhs non-negative, otherwise the problem is infeasible */
659  if ( lplhsafterfix[*nactivelpcons] > sdpi->feastol || lprhsafterfix[*nactivelpcons] < -sdpi->feastol )
660  {
661  sdpi->infeasible = TRUE;
662  SCIPdebugMessage("We found a constraint which with given fixings reads %f <= 0 <= %f, so the current problem is infeasible !\n",
663  lplhsafterfix[*nactivelpcons], lprhsafterfix[*nactivelpcons] );
664  return SCIP_OKAY;
665  }
666  }
667 
668  /* update lastrow for new row */
669  lastrow = sdpi->lprow[i];
670 
671  /* start the next lhr & rhs with the original value */
672  lplhsafterfix[*nactivelpcons] = sdpi->lplhs[lastrow];
673  lprhsafterfix[*nactivelpcons] = sdpi->lprhs[lastrow];
674  }
675 
676  /* if the variable is active, we increase rownactivevars */
677  if ( ! isFixed(sdpi, sdpi->lpcol[i]) )
678  {
679  rownactivevars[lastrow]++;
680  nonzind = i;
681  }
682  else
683  {
684  /* otherwise we add the value (coefficient * value of fixed variable) to the lhs and rhs, the minus comes from +A_i but -A_0 */
685  lplhsafterfix[*nactivelpcons] -= sdpi->lpval[i] * sdpi->lb[sdpi->lpcol[i]];
686  lprhsafterfix[*nactivelpcons] -= sdpi->lpval[i] * sdpi->lb[sdpi->lpcol[i]];
687  }
688  }
689 
690  /* for the last row of the lp we have to check if it is active, as in the above for-queue we only do so when the next row start */
691  if ( rownactivevars[lastrow] > 1 )
692  (*nactivelpcons)++;
693  else if ( rownactivevars[lastrow] == 1 )
694  {
695  assert( 0 <= nonzind && nonzind < sdpi->lpnnonz );
696 
697  nonzcol = sdpi->lpcol[nonzind];
698  assert( 0 <= nonzcol && nonzcol < sdpi->nvars );
699 
700  nonzval = sdpi->lpval[nonzind];
701  assert( REALABS(nonzval) > sdpi->feastol );
702 
703  /* we have to check if this is an improvement of the current bound */
704  if ( nonzval < 0.0 ) /* we have to compare with the upper bound for lhs and lower bound for rhs */
705  {
706  /* check for the left-hand-side */
707  if ( (lplhsafterfix[*nactivelpcons] > SCIPsdpiInfinity(sdpi)) &&
708  ( (lplhsafterfix[*nactivelpcons] / nonzval) < sdpi->ub[nonzcol] - sdpi->feastol) )
709  {
710  /* this bound is sharper than the original one */
711  SCIPdebugMessage("empty LP-row %d has been removed from SDP %d, upper bound of variable %d has been sharpened to %f "
712  "(originally %f)\n", lastrow, sdpi->sdpid, nonzcol, lplhsafterfix[*nactivelpcons] / nonzval, sdpi->ub[nonzcol]);
713  sdpi->ub[nonzcol] = lplhsafterfix[*nactivelpcons] / nonzval;
714 
715  /* check if this leads to a fixing of this variable */
716  if ( REALABS(sdpi->lb[nonzcol] - sdpi->ub[nonzcol]) < sdpi->feastol )
717  {
718  *fixingsfound = TRUE;
719  SCIPdebugMessage("computeLpLhsRhsAfterFixings fixed variable %d to value %f in SDP %d\n",
720  nonzcol, sdpi->lb[nonzcol], sdpi->sdpid);
721  }
722 
723  /* check if this makes the problem infeasible */
724  if ( sdpi->ub[nonzcol] < sdpi->lb[nonzcol] - sdpi->feastol )
725  {
726  sdpi->infeasible = TRUE;
727  SCIPdebugMessage("We found an upper bound that is lower than the lower bound, so the problem is infeasible !\n");
728  return SCIP_OKAY;
729  }
730  }
731  /* check for the right-hand-side */
732  if ( (lprhsafterfix[*nactivelpcons] < SCIPsdpiInfinity(sdpi)) &&
733  ( (lprhsafterfix[*nactivelpcons] / nonzval) > sdpi->lb[nonzcol] - sdpi->feastol) )
734  {
735  /* this bound is sharper than the original one */
736  SCIPdebugMessage("empty LP-row %d has been removed from SDP %d, lower bound of variable %d has been sharpened to %f "
737  "(originally %f)\n", lastrow, sdpi->sdpid, nonzcol, lprhsafterfix[*nactivelpcons] / nonzval, sdpi->lb[nonzcol]);
738  sdpi->lb[nonzcol] = lprhsafterfix[*nactivelpcons] / nonzval;
739 
740  /* check if this leads to a fixing of this variable */
741  if ( REALABS(sdpi->lb[nonzcol] - sdpi->ub[nonzcol]) < sdpi->feastol )
742  {
743  *fixingsfound = TRUE;
744  SCIPdebugMessage("computeLpLhsRhsAfterFixings fixed variable %d to value %f in SDP %d\n",
745  nonzcol, sdpi->lb[nonzcol], sdpi->sdpid);
746  }
747 
748  /* check if this makes the problem infeasible */
749  if ( sdpi->ub[nonzcol] < sdpi->lb[nonzcol] - sdpi->feastol )
750  {
751  sdpi->infeasible = TRUE;
752  SCIPdebugMessage("We found an upper bound that is lower than the lower bound, so the problem is infeasible !\n");
753  return SCIP_OKAY;
754  }
755  }
756  }
757  else /* we compare with the lower bound for lhs and upper bound for rhs */
758  {
759  /* check for the left-hand-side */
760  if ( (lplhsafterfix[*nactivelpcons] < SCIPsdpiInfinity(sdpi)) &&
761  ( (lplhsafterfix[*nactivelpcons] / nonzval) > sdpi->lb[nonzcol] + sdpi->feastol) )
762  {
763  /* this bound is sharper than the original one */
764  SCIPdebugMessage("empty LP-row %d has been removed from SDP %d, lower bound of variable %d has been sharpened to %f "
765  "(originally %f)\n", lastrow, sdpi->sdpid, nonzcol, lplhsafterfix[*nactivelpcons] / nonzval, sdpi->lb[nonzcol]);
766  sdpi->lb[nonzcol] = lplhsafterfix[*nactivelpcons] / nonzval;
767 
768  /* check if this leads to a fixing of this variable */
769  if ( REALABS(sdpi->lb[nonzcol] - sdpi->ub[nonzcol]) < sdpi->feastol )
770  {
771  *fixingsfound = TRUE;
772  SCIPdebugMessage("computeLpLhsRhsAfterFixings fixed variable %d to value %f in SDP %d\n",
773  nonzcol, sdpi->lb[nonzcol], sdpi->sdpid);
774  }
775 
776  /* check if this makes the problem infeasible */
777  if ( sdpi->ub[nonzcol] < sdpi->lb[nonzcol] - sdpi->feastol )
778  {
779  sdpi->infeasible = TRUE;
780  SCIPdebugMessage("We found a lower bound that is bigger than the upper bound, so the problem is infeasible !\n");
781  return SCIP_OKAY;
782  }
783  }
784  /* check for the right-hand-side */
785  if ( (lprhsafterfix[*nactivelpcons] > SCIPsdpiInfinity(sdpi)) &&
786  ( (lprhsafterfix[*nactivelpcons] / nonzval) < sdpi->ub[nonzcol] - sdpi->feastol) )
787  {
788  /* this bound is sharper than the original one */
789  SCIPdebugMessage("empty LP-row %d has been removed from SDP %d, upper bound of variable %d has been sharpened to %f "
790  "(originally %f)\n", lastrow, sdpi->sdpid, nonzcol, lprhsafterfix[*nactivelpcons] / nonzval, sdpi->ub[nonzcol]);
791  sdpi->ub[nonzcol] = lplhsafterfix[*nactivelpcons] / nonzval;
792 
793  /* check if this leads to a fixing of this variable */
794  if ( REALABS(sdpi->lb[nonzcol] - sdpi->ub[nonzcol]) < sdpi->feastol )
795  {
796  *fixingsfound = TRUE;
797  SCIPdebugMessage("computeLpLhsRhsAfterFixings fixed variable %d to value %f in SDP %d\n",
798  nonzcol, sdpi->lb[nonzcol], sdpi->sdpid);
799  }
800 
801  /* check if this makes the problem infeasible */
802  if ( sdpi->ub[nonzcol] < sdpi->lb[nonzcol] - sdpi->feastol )
803  {
804  sdpi->infeasible = TRUE;
805  SCIPdebugMessage("We found an upper bound that is lower than the lower bound, so the problem is infeasible !\n");
806  return SCIP_OKAY;
807  }
808  }
809  }
810  }
811  else
812  {
813  assert( lastrow == -1 || rownactivevars[lastrow] == 0 );
814  /* we have a constraint lhs <= 0 <= rhs, so lhs should be non-positive and rhs non-negative, otherwise the problem is infeasible */
815  if ( lplhsafterfix[*nactivelpcons] > sdpi->feastol || lprhsafterfix[*nactivelpcons] < -sdpi->feastol )
816  {
817  sdpi->infeasible = TRUE;
818  SCIPdebugMessage("We found a constraint which with given fixings reads %f <= 0 <= %f, so the current problem is infeasible !\n",
819  lplhsafterfix[*nactivelpcons], lprhsafterfix[*nactivelpcons] );
820  return SCIP_OKAY;
821  }
822  }
823 
824  return SCIP_OKAY;
825 }
826 
829 static
830 SCIP_RETCODE checkAllFixed(
831  SCIP_SDPI* sdpi
832  )
833 {
834  int v;
835 
836  /* check all variables until we find an unfixed one */
837  for (v = 0; v < sdpi->nvars; v++)
838  {
839  if ( ! isFixed(sdpi, v) )
840  {
841  sdpi->allfixed = FALSE;
842 
843  return SCIP_OKAY;
844  }
845  }
846 
847  /* we did not find an unfixed variable, so all are fixed */
848  SCIPdebugMessage("Detected that all variables in SDP %d are fixed.\n", sdpi->sdpid);
849  sdpi->allfixed = TRUE;
850 
851  return SCIP_OKAY;
852 }
853 
857 static
859  SCIP_SDPI* sdpi,
860  int* sdpconstnblocknonz,
862  int** sdpconstrow,
863  int** sdpconstcol,
864  SCIP_Real** sdpconstval,
865  int** indchanges,
869  int* nremovedinds,
870  int* blockindchanges
871  )
872 {
873  SCIP_Real* fullmatrix; /* we need to give the full matrix to LAPACK */
874  int maxsize; /* as we don't want to allocate memory newly for every SDP-block, we allocate memory according to the size of the largest block */
875  SCIP_Real fixedval;
876  SCIP_Real eigenvalue;
877  int size;
878  int b;
879  int i;
880  int v;
881 
882  assert( sdpi->allfixed );
883 
884  /* compute the maximum blocksize */
885  maxsize = -1;
886 
887  for (b = 0; b < sdpi->nsdpblocks; b++)
888  {
889  if ( sdpi->sdpblocksizes[b] - nremovedinds[b] > maxsize )
890  maxsize = sdpi->sdpblocksizes[b] - nremovedinds[b];
891  }
892 
893  /* allocate memory */
894  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &fullmatrix, maxsize * maxsize) ); /*lint !e647*/
895 
896  /* iterate over all SDP-blocks and check if the smallest eigenvalue is non-negative */
897  for (b = 0; b < sdpi->nsdpblocks; b++)
898  {
899  /* if the block is removed, we don't need to do anything, otherwise build the full matrix */
900  if ( blockindchanges[b] == -1 )
901  continue;
902 
903  size = sdpi->sdpblocksizes[b] - nremovedinds[b];
904 
905  /* initialize the matrix with zero */
906  for (i = 0; i < size * size; i++)
907  fullmatrix[i] = 0.0;
908 
909  /* add the constant part (with negative sign) */
910  for (i = 0; i < sdpconstnblocknonz[b]; i++)
911  {
912  assert( 0 <= sdpconstrow[b][i] - indchanges[b][sdpconstrow[b][i]] && sdpconstrow[b][i] - indchanges[b][sdpconstrow[b][i]] < size );
913  assert( 0 <= sdpconstcol[b][i] - indchanges[b][sdpconstcol[b][i]] && sdpconstcol[b][i] - indchanges[b][sdpconstcol[b][i]] < size );
914  fullmatrix[(sdpconstrow[b][i] - indchanges[b][sdpconstrow[b][i]]) * size
915  + sdpconstcol[b][i] - indchanges[b][sdpconstcol[b][i]]] = -1 * sdpconstval[b][i]; /*lint !e679*/
916  }
917 
918  /* add the contributions of the fixed variables */
919  for (v = 0; v < sdpi->sdpnblockvars[b]; v++)
920  {
921  fixedval = sdpi->lb[sdpi->sdpvar[b][v]];
922 
923  /* if the variable is fixed to zero, we can ignore its contributions */
924  if ( REALABS(fixedval) < sdpi->feastol )
925  continue;
926 
927  /* iterate over all nonzeros */
928  for (i = 0; i < sdpi->sdpnblockvarnonz[b][v]; i++)
929  {
930  assert( 0 <= sdpi->sdprow[b][v][i] - indchanges[b][sdpi->sdprow[b][v][i]] &&
931  sdpi->sdprow[b][v][i] - indchanges[b][sdpi->sdprow[b][v][i]] < size );
932  assert( 0 <= sdpi->sdpcol[b][v][i] - indchanges[b][sdpi->sdpcol[b][v][i]] &&
933  sdpi->sdpcol[b][v][i] - indchanges[b][sdpi->sdpcol[b][v][i]] < size );
934  fullmatrix[(sdpi->sdprow[b][v][i] - indchanges[b][sdpi->sdprow[b][v][i]]) * size
935  + sdpi->sdpcol[b][v][i] - indchanges[b][sdpi->sdpcol[b][v][i]]] += fixedval * sdpi->sdpval[b][v][i]; /*lint !e679*/
936  }
937  }
938 
939  /* compute the smallest eigenvalue */
940  SCIP_CALL( SCIPlapackComputeIthEigenvalue(sdpi->blkmem, FALSE, size, fullmatrix, 1, &eigenvalue, NULL) );
941 
942  /* check if the eigenvalue is negative */
943  if ( eigenvalue < -1 * sdpi->feastol )
944  {
945  sdpi->infeasible = TRUE;
946  SCIPdebugMessage("Detected infeasibility for SDP %d with all fixed variables!\n", sdpi->sdpid);
947  break;
948  }
949  }
950 
951  /* free memory */
952  BMSfreeBlockMemoryArray(sdpi->blkmem, &fullmatrix, maxsize * maxsize);/*lint !e737*//*lint !e647*/
953 
954  /* if we didn't find an SDP-block with negative eigenvalue, the solution is feasible */
955  sdpi->infeasible = FALSE;
956  SCIPdebugMessage("Unique solution for SDP %d with all fixed variables is feasible!\n", sdpi->sdpid);
957 
958  return SCIP_OKAY;
959 }
960 
963 static
964 SCIP_RETCODE checkSlaterCondition(
965  SCIP_SDPI* sdpi,
966  SCIP_Real timelimit,
967  clock_t starttime,
968  int* sdpconstnblocknonz,
970  int** sdpconstrow,
971  int** sdpconstcol,
972  SCIP_Real** sdpconstval,
973  int** indchanges,
975  int* nremovedinds,
976  SCIP_Real* lplhsafterfix,
977  SCIP_Real* lprhsafterfix,
978  int* rowsnactivevars,
979  int* blockindchanges,
981  int sdpconstnnonz,
982  int nactivelpcons,
983  int nremovedblocks,
984  SCIP_Bool rootnodefailed
986  )
987 {
988  SCIP_Real objval;
989  SCIP_Bool origfeas = FALSE;
990  SCIP_Bool penaltybound = FALSE;
991  int* slaterlprow;
992  int* slaterlpcol;
993  SCIP_Real* slaterlpval;
994  SCIP_Real* slaterlplhs;
995  SCIP_Real* slaterlprhs;
996  int* slaterrowsnactivevars;
997  int nremovedslaterlpinds;
998  int i;
999  int v;
1000  int b;
1001  int slaternactivelpcons;
1002  SCIP_Real* slaterlb;
1003  SCIP_Real* slaterub;
1004  int slaternremovedvarbounds;
1005  SCIP_Real solvertimelimit;
1006  clock_t currenttime;
1007 
1008  assert( sdpi != NULL );
1009  assert( sdpconstnnonz == 0 || sdpconstnblocknonz != NULL );
1010  assert( sdpconstnnonz == 0 || sdpconstrow != NULL );
1011  assert( sdpconstnnonz == 0 || sdpconstcol != NULL );
1012  assert( sdpconstnnonz == 0 || sdpconstval != NULL );
1013  assert( sdpi->nsdpblocks == 0 || indchanges != NULL );
1014  assert( sdpi->nsdpblocks == 0 || nremovedinds != NULL );
1015  assert( nactivelpcons == 0 || lplhsafterfix != NULL );
1016  assert( nactivelpcons == 0 || lprhsafterfix != NULL );
1017  assert( sdpi->nlpcons == 0 || rowsnactivevars != NULL );
1018  assert( sdpi->nsdpblocks == 0 || blockindchanges != NULL );
1019 
1020  /* first check the Slater condition for the dual problem */
1021 
1022  /* compute the timit limit to set for the solver */
1023  solvertimelimit = timelimit;
1024  if ( ! SCIPsdpiIsInfinity(sdpi, solvertimelimit) )
1025  {
1026  currenttime = clock();
1027  solvertimelimit -= (SCIP_Real)(currenttime - starttime) / (SCIP_Real) CLOCKS_PER_SEC;/*lint !e620*/
1028  }
1029 
1030  /* we solve the problem with a slack variable times identity added to the constraints and trying to minimize this slack variable r, if we are
1031  * still feasible for r > feastol, then we have an interior point with smallest eigenvalue > feastol, otherwise the Slater condition is harmed */
1032  SCIP_CALL( SCIPsdpiSolverLoadAndSolveWithPenalty(sdpi->sdpisolver, 1.0, FALSE, FALSE, sdpi->nvars, sdpi->obj, sdpi->lb, sdpi->ub,
1033  sdpi->nsdpblocks, sdpi->sdpblocksizes, sdpi->sdpnblockvars, sdpconstnnonz,
1034  sdpconstnblocknonz, sdpconstrow, sdpconstcol, sdpconstval,
1035  sdpi->sdpnnonz, sdpi->sdpnblockvarnonz, sdpi->sdpvar, sdpi->sdprow, sdpi->sdpcol,
1036  sdpi->sdpval, indchanges, nremovedinds, blockindchanges, nremovedblocks, nactivelpcons, sdpi->nlpcons, lplhsafterfix, lprhsafterfix,
1037  rowsnactivevars, sdpi->lpnnonz, sdpi->lprow, sdpi->lpcol, sdpi->lpval, NULL, SCIP_SDPSOLVERSETTING_UNSOLVED, solvertimelimit,
1038  &origfeas, &penaltybound) );
1039 
1040  if ( ! SCIPsdpiSolverIsOptimal(sdpi->sdpisolver) && ! SCIPsdpiSolverIsDualUnbounded(sdpi->sdpisolver) && ! SCIPsdpiSolverIsDualInfeasible(sdpi->sdpisolver) )
1041  {
1042  if ( rootnodefailed )
1043  {
1044  SCIPmessagePrintInfo(sdpi->messagehdlr, "Aborting due to failing to solve the root node relaxation, Slater condition for the dual problem could "
1045  "not be checked, ");
1046  }
1047  else if ( sdpi->slatercheck == 2 )
1048  SCIPmessagePrintInfo(sdpi->messagehdlr, "Unable to check Slater condition for dual problem.\n");
1049  sdpi->dualslater = SCIP_SDPSLATER_NOINFO;
1050  }
1051  else
1052  {
1053  if ( SCIPsdpiSolverIsDualUnbounded(sdpi->sdpisolver) )
1054  {
1055  if ( rootnodefailed )
1056  SCIPmessagePrintInfo(sdpi->messagehdlr, "Aborting due to failing to solve the root node relaxation, Slater condition for the dual problem holds "
1057  "as smallest eigenvalue maximization problem is unbounded, ");
1058  else
1059  SCIPdebugMessage("Slater condition for dual problem for SDP %d fullfilled, smallest eigenvalue maximization problem unbounded.\n", sdpi->sdpid);
1060  sdpi->dualslater = SCIP_SDPSLATER_HOLDS;
1061  }
1062  else if ( SCIPsdpiSolverIsDualInfeasible(sdpi->sdpisolver) )
1063  {
1064  if ( rootnodefailed )
1065  {
1066  SCIPmessagePrintInfo(sdpi->messagehdlr, "Aborting due to failing to solve the root node relaxation, Slater condition for the dual problem "
1067  "not fullfilled as problem is infeasible, ");
1068  }
1069  else if ( sdpi->slatercheck == 2 )
1070  SCIPmessagePrintInfo(sdpi->messagehdlr, "Slater condition for dual problem for SDP %d not fullfilled, problem infeasible.\n", sdpi->sdpid);
1071  sdpi->dualslater = SCIP_SDPSLATER_NOT;
1072  }
1073  else
1074  {
1075  SCIP_CALL( SCIPsdpiSolverGetObjval(sdpi->sdpisolver, &objval) );
1076 
1077  if ( objval < - sdpi->feastol )
1078  {
1079  if ( rootnodefailed )
1080  {
1081  SCIPmessagePrintInfo(sdpi->messagehdlr, "Aborting due to failing to solve the root node relaxation, Slater condition for the dual problem holds"
1082  "with smallest eigenvalue %f, ", -1.0 * objval);
1083  }
1084  else
1085  SCIPdebugMessage("Slater condition for SDP %d is fullfilled for dual problem with smallest eigenvalue %f.\n", sdpi->sdpid, -1.0 * objval);
1086  sdpi->dualslater = SCIP_SDPSLATER_HOLDS;
1087  }
1088  else if ( objval < sdpi->epsilon )
1089  {
1090  if ( rootnodefailed )
1091  {
1092  SCIPmessagePrintInfo(sdpi->messagehdlr, "Aborting due to failing to solve the root node relaxation, Slater condition for the dual problem "
1093  "not fullfilled with smallest eigenvalue %f, ", -1.0 * objval);
1094  }
1095  else if ( sdpi->slatercheck == 2 )
1096  {
1097  SCIPmessagePrintInfo(sdpi->messagehdlr, "Slater condition for SDP %d not fullfilled for dual problem as smallest eigenvalue was %f, expect numerical trouble.\n",
1098  sdpi->sdpid, -1.0 * objval);
1099  }
1100  sdpi->dualslater = SCIP_SDPSLATER_NOT;
1101  }
1102  else
1103  {
1104  if ( sdpi->slatercheck == 2 )
1105  {
1106  SCIPmessagePrintInfo(sdpi->messagehdlr, "Slater condition for SDP %d not fullfilled for dual problem as smallest eigenvalue was %f, problem is infeasible.\n",
1107  sdpi->sdpid, -1.0 * objval);
1108  }
1109  sdpi->dualslater = SCIP_SDPSLATER_INF;
1110  }
1111  }
1112  }
1113 
1114  /* check the Slater condition also for the primal problem */
1115 
1116  /* As we do not want to give equality constraints to the solver by reformulating the primal problem as a dual problem, we instead
1117  * solve the primal dual pair
1118  *
1119  * (P) max (0 0) * Y' s.t. (A_i 0 ) * Y' = c_i forall i, Y' psd
1120  * (0 1) ( 0 sum_j [(A_i)_jj])
1121  *
1122  * (D) min sum_i [c_i x_i] s.t. sum_i [A_i x_i] psd, sum_i[(sum_j [(A_i)_jj]) x_i] >= 1
1123  *
1124  * where we also set all finite lhs/rhs of all lp-constraints and varbounds to zero.
1125  * If the objective is strictly positive, than we now that there exists some r > 0 such that
1126  * Y is psd and Y+rI is feasible for the equality constraints in our original primal problem,
1127  * so Y+rI is also feasible for the original primal problem and is strictly positive definite
1128  * so the primal Slater condition holds
1129  */
1130 
1131  /* allocate the LP-arrays, as we have to add the additional LP-constraint, because we want to add extra entries, we cannot use BMSduplicate... */
1132  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &slaterlprow, sdpi->lpnnonz + sdpi->nvars) );/*lint !e776*/
1133  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &slaterlpcol, sdpi->lpnnonz + sdpi->nvars) );/*lint !e776*/
1134  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &slaterlpval, sdpi->lpnnonz + sdpi->nvars) );/*lint !e776*/
1135 
1136  /* copy all old LP-entries */
1137  for (i = 0; i < sdpi->lpnnonz; i++)
1138  {
1139  slaterlprow[i] = sdpi->lprow[i];
1140  slaterlpcol[i] = sdpi->lpcol[i];
1141  slaterlpval[i] = sdpi->lpval[i];
1142  }
1143 
1144  /* add the new entries sum_j [(A_i)_jj], for this we have to iterate over the whole sdp-matrices (for all blocks), adding all diagonal entries */
1145  for (v = 0; v < sdpi->nvars; v++)
1146  {
1147  slaterlprow[sdpi->lpnnonz + v] = sdpi->nlpcons;/*lint !e679*/
1148  slaterlpcol[sdpi->lpnnonz + v] = v;/*lint !e679*/
1149  slaterlpval[sdpi->lpnnonz + v] = 0.0;/*lint !e679*/
1150  }
1151  for (b = 0; b < sdpi->nsdpblocks; b++)
1152  {
1153  for (v = 0; v < sdpi->sdpnblockvars[b]; v++)
1154  {
1155  for (i = 0; i < sdpi->sdpnblockvarnonz[b][v]; i++)
1156  {
1157  if ( sdpi->sdprow[b][v][i] == sdpi->sdpcol[b][v][i] ) /* it is a diagonal entry */
1158  slaterlpval[sdpi->lpnnonz + sdpi->sdpvar[b][v]] += sdpi->sdpval[b][v][i];/*lint !e679*/
1159  }
1160  }
1161  }
1162 
1163  /* iterate over all added LP-entries and remove all zeros (by shifting further variables) */
1164  nremovedslaterlpinds = 0;
1165  for (v = 0; v < sdpi->nvars; v++)
1166  {
1167  if ( REALABS(slaterlpval[sdpi->lpnnonz + v]) <= sdpi->feastol )/*lint !e679*/
1168  nremovedslaterlpinds++;
1169  else
1170  {
1171  /* shift the entries */
1172  slaterlprow[sdpi->lpnnonz + v - nremovedslaterlpinds] = slaterlprow[sdpi->lpnnonz + v];/*lint !e679*/
1173  slaterlpcol[sdpi->lpnnonz + v - nremovedslaterlpinds] = slaterlpcol[sdpi->lpnnonz + v];/*lint !e679*/
1174  slaterlpval[sdpi->lpnnonz + v - nremovedslaterlpinds] = slaterlpval[sdpi->lpnnonz + v];/*lint !e679*/
1175  }
1176  }
1177 
1178  /* allocate memory for l/r-hs */
1179  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &slaterlplhs, nactivelpcons + 1) );/*lint !e776*/
1180  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &slaterlprhs, nactivelpcons + 1) );/*lint !e776*/
1181 
1182  /* set the old entries to zero (if existing), as A_0 (including the LP-part) is removed because of the changed primal objective */
1183  for (i = 0; i < nactivelpcons; i++)
1184  {
1185  if ( SCIPsdpiSolverIsInfinity(sdpi->sdpisolver, lplhsafterfix[i]) )
1186  slaterlplhs[i] = lplhsafterfix[i];
1187  else
1188  slaterlplhs[i] = 0.0;
1189 
1190  if ( SCIPsdpiSolverIsInfinity(sdpi->sdpisolver, lprhsafterfix[i]) )
1191  slaterlprhs[i] = lprhsafterfix[i];
1192  else
1193  slaterlprhs[i] = 0.0;
1194  }
1195 
1196  /* add the new ones */
1197  slaterlplhs[nactivelpcons] = 1.0;
1198  slaterlprhs[nactivelpcons] = SCIPsdpiSolverInfinity(sdpi->sdpisolver);
1199 
1200  /* allocate memory for rowsnactivevars to update it for the added row */
1201  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &slaterrowsnactivevars, sdpi->nlpcons + 1) );/*lint !e776*/
1202 
1203  /* copy the old entries */
1204  for (i = 0; i < sdpi->nlpcons; i++)
1205  slaterrowsnactivevars[i] = rowsnactivevars[i];
1206 
1207  /* add the new entry (this equals the number of active variables) */
1208  slaterrowsnactivevars[sdpi->nlpcons] = 0;
1209  for (v = 0; v < sdpi->nvars; v++)
1210  {
1211  if ( ! (isFixed(sdpi, v)) )
1212  slaterrowsnactivevars[sdpi->nlpcons]++;
1213  }
1214 
1215  slaternactivelpcons = (slaterrowsnactivevars[sdpi->nlpcons] > 1) ? nactivelpcons + 1 : nactivelpcons;
1216 
1217  /* copy the varbound arrays to change all finite varbounds to zero */
1218  DUPLICATE_ARRAY_NULL(sdpi->blkmem, &slaterlb, sdpi->lb, sdpi->nvars);
1219  DUPLICATE_ARRAY_NULL(sdpi->blkmem, &slaterub, sdpi->ub, sdpi->nvars);
1220 
1221  /* set all finite varbounds to zero */
1222  slaternremovedvarbounds = 0;
1223  for (v = 0; v < sdpi->nvars; v++)
1224  {
1225  if ( slaterlb[v] > -1 * SCIPsdpiSolverInfinity(sdpi->sdpisolver) )
1226  {
1227  slaterlb[v] = 0.0;
1228  slaternremovedvarbounds++;
1229  }
1230  if ( slaterub[v] < SCIPsdpiSolverInfinity(sdpi->sdpisolver) )
1231  {
1232  slaterub[v] = 0.0;
1233  slaternremovedvarbounds++;
1234  }
1235  }
1236 
1237  /* if all variables have finite upper and lower bounds these add variables to every constraint of the
1238  * primal problem that allow us to make the problem feasible for every primal matrix X, so the primal
1239  * Slater condition holds */
1240  if ( slaternremovedvarbounds == 2 * sdpi->nvars )
1241  {
1242  if ( rootnodefailed )
1243  {
1244  SCIPmessagePrintInfo(sdpi->messagehdlr, "Slater condition for primal problem holds since all variables have finite upper and lower bounds \n");
1245  }
1246  else
1247  SCIPdebugMessage("Slater condition for primal problem for SDP %d fullfilled as all variables have finite upper and lower bounds \n",sdpi->sdpid);
1248  sdpi->primalslater = SCIP_SDPSLATER_HOLDS;
1249  }
1250  else
1251  {
1252  /* compute the timit limit to set for the solver */
1253  currenttime = clock();
1254  solvertimelimit = timelimit - ((SCIP_Real)(currenttime - starttime) / (SCIP_Real) CLOCKS_PER_SEC); /*lint !e620*/
1255 
1256  /* solve the problem to check Slater condition for primal of original problem */
1257  SCIP_CALL( SCIPsdpiSolverLoadAndSolve(sdpi->sdpisolver, sdpi->nvars, sdpi->obj, slaterlb, slaterub,
1258  sdpi->nsdpblocks, sdpi->sdpblocksizes, sdpi->sdpnblockvars, 0, NULL, NULL, NULL, NULL,
1259  sdpi->sdpnnonz, sdpi->sdpnblockvarnonz, sdpi->sdpvar, sdpi->sdprow, sdpi->sdpcol,
1260  sdpi->sdpval, indchanges, nremovedinds, blockindchanges, nremovedblocks, slaternactivelpcons, sdpi->nlpcons + 1, slaterlplhs, slaterlprhs,
1261  slaterrowsnactivevars, sdpi->lpnnonz + sdpi->nvars - nremovedslaterlpinds, slaterlprow, slaterlpcol, slaterlpval, NULL,
1262  SCIP_SDPSOLVERSETTING_UNSOLVED, solvertimelimit) );
1263 
1264  if ( ! SCIPsdpiSolverIsOptimal(sdpi->sdpisolver) && ! SCIPsdpiSolverIsDualUnbounded(sdpi->sdpisolver) && ! SCIPsdpiSolverIsPrimalUnbounded(sdpi->sdpisolver) )
1265  {
1266  if ( rootnodefailed )
1267  {
1268  SCIPmessagePrintInfo(sdpi->messagehdlr, "unable to check Slater condition for primal problem \n");
1269  }
1270  else if ( sdpi->slatercheck == 2 )
1271  SCIPmessagePrintInfo(sdpi->messagehdlr, "Unable to check Slater condition for primal problem, could not solve auxilliary problem.\n");
1272  sdpi->primalslater = SCIP_SDPSLATER_NOINFO;
1273  }
1274  else if ( SCIPsdpiSolverIsDualUnbounded(sdpi->sdpisolver) )
1275  {
1276  if ( rootnodefailed )
1277  {
1278  SCIPmessagePrintInfo(sdpi->messagehdlr, " primal Slater condition shows infeasibility \n");
1279  }
1280  else if ( sdpi->slatercheck == 2 )
1281  {
1282  SCIPmessagePrintInfo(sdpi->messagehdlr, "Slater condition for primal problem for SDP %d not fullfilled "
1283  "smallest eigenvalue has to be negative, so primal problem is infeasible (if the dual slater condition holds,"
1284  "this means, that the original (dual) problem is unbounded.\n",sdpi->sdpid);
1285  }
1286  sdpi->primalslater = SCIP_SDPSLATER_NOT;
1287  }
1288  else if ( SCIPsdpiSolverIsPrimalUnbounded(sdpi->sdpisolver) )
1289  {
1290  if ( rootnodefailed )
1291  {
1292  SCIPmessagePrintInfo(sdpi->messagehdlr, "Slater condition for primal problems holds sunce smallest eigenvalue maximization problem"
1293  "is unbounded \n");
1294  }
1295  else
1296  SCIPdebugMessage("Slater condition for primal problem for SDP %d fullfilled, smallest eigenvalue maximization problem unbounded \n",sdpi->sdpid);
1297  sdpi->primalslater = SCIP_SDPSLATER_HOLDS;
1298  }
1299  else
1300  {
1301  SCIP_CALL( SCIPsdpiSolverGetObjval(sdpi->sdpisolver, &objval) );
1302 
1303  if ( objval > - sdpi->feastol)
1304  {
1305  if ( rootnodefailed )
1306  {
1307  SCIPmessagePrintInfo(sdpi->messagehdlr, "Slater condition for primal problem not fullfilled with smallest eigenvalue %f \n", -1.0 * objval);
1308  }
1309  else if ( sdpi->slatercheck == 2 )
1310  {
1311  SCIPmessagePrintInfo(sdpi->messagehdlr, "Slater condition for primal problem for SDP %d not fullfilled "
1312  "as smallest eigenvalue was %f, expect numerical trouble or infeasible problem.\n",sdpi->sdpid, -1.0 * objval);
1313  }
1314  sdpi->primalslater = SCIP_SDPSLATER_NOT;
1315  }
1316  else
1317  {
1318  if ( rootnodefailed )
1319  {
1320  SCIPmessagePrintInfo(sdpi->messagehdlr, "Slater condition for primal problem fullfilled with smallest eigenvalue %f \n", -1.0 * objval);
1321  }
1322  else
1323  SCIPdebugMessage("Slater condition for primal problem of SDP %d is fullfilled with smallest eigenvalue %f.\n", sdpi->sdpid, -1.0 * objval);
1324  sdpi->primalslater = SCIP_SDPSLATER_HOLDS;
1325  }
1326  }
1327  }
1328 
1329  /* free all memory */
1330  BMSfreeBlockMemoryArray(sdpi->blkmem, &slaterub, sdpi->nvars);/*lint !e737*/
1331  BMSfreeBlockMemoryArray(sdpi->blkmem, &slaterlb, sdpi->nvars);/*lint !e737*/
1332  BMSfreeBlockMemoryArray(sdpi->blkmem, &slaterrowsnactivevars, sdpi->nlpcons + 1);/*lint !e737*//*lint !e776*/
1333  BMSfreeBlockMemoryArray(sdpi->blkmem, &slaterlprhs, nactivelpcons + 1);/*lint !e737*//*lint !e776*/
1334  BMSfreeBlockMemoryArray(sdpi->blkmem, &slaterlplhs, nactivelpcons + 1);/*lint !e737*//*lint !e776*/
1335  BMSfreeBlockMemoryArray(sdpi->blkmem, &slaterlpval, sdpi->lpnnonz + sdpi->nvars);/*lint !e737*//*lint !e776*/
1336  BMSfreeBlockMemoryArray(sdpi->blkmem, &slaterlpcol, sdpi->lpnnonz + sdpi->nvars);/*lint !e737*//*lint !e776*/
1337  BMSfreeBlockMemoryArray(sdpi->blkmem, &slaterlprow, sdpi->lpnnonz + sdpi->nvars);/*lint !e737*//*lint !e776*/
1338 
1339  return SCIP_OKAY;
1340 }
1341 
1342 /*
1343  * Miscellaneous Methods
1344  */
1345 
1352  void
1353  )
1354 {
1355  return SCIPsdpiSolverGetSolverName();
1356 }
1357 
1360  void
1361  )
1362 {
1363  return SCIPsdpiSolverGetSolverDesc();
1364 }
1365 
1373  SCIP_SDPI* sdpi
1374  )
1375 {
1376  return SCIPsdpiSolverGetSolverPointer(sdpi->sdpisolver);
1377 }
1378 
1382 /*
1383  * SDPI Creation and Destruction Methods
1384  */
1385 
1390 SCIP_RETCODE SCIPsdpiCreate(
1391  SCIP_SDPI** sdpi,
1392  SCIP_MESSAGEHDLR* messagehdlr,
1393  BMS_BLKMEM* blkmem
1394  )
1395 {
1396  assert ( sdpi != NULL );
1397  assert ( blkmem != NULL );
1398 
1399  SCIPdebugMessage("Calling SCIPsdpiCreate\n");
1400 
1401  BMS_CALL( BMSallocBlockMemory(blkmem, sdpi) );
1402 
1403  SCIP_CALL( SCIPsdpiSolverCreate(&((*sdpi)->sdpisolver), messagehdlr, blkmem) );
1404 
1405  (*sdpi)->messagehdlr = messagehdlr;
1406  (*sdpi)->blkmem = blkmem;
1407  (*sdpi)->sdpid = 1;
1408  (*sdpi)->niterations = 0;
1409  (*sdpi)->nsdpcalls = 0;
1410  (*sdpi)->nvars = 0;
1411  (*sdpi)->nsdpblocks = 0;
1412  (*sdpi)->sdpconstnnonz = 0;
1413  (*sdpi)->sdpnnonz = 0;
1414  (*sdpi)->nlpcons = 0;
1415  (*sdpi)->lpnnonz = 0;
1416  (*sdpi)->slatercheck = 0;
1417  (*sdpi)->solved = FALSE;
1418  (*sdpi)->penalty = FALSE;
1419  (*sdpi)->infeasible = FALSE;
1420  (*sdpi)->allfixed = FALSE;
1421 
1422  (*sdpi)->obj = NULL;
1423  (*sdpi)->lb = NULL;
1424  (*sdpi)->ub = NULL;
1425  (*sdpi)->sdpblocksizes = NULL;
1426  (*sdpi)->sdpnblockvars = NULL;
1427  (*sdpi)->sdpconstnblocknonz = NULL;
1428  (*sdpi)->sdpconstrow = NULL;
1429  (*sdpi)->sdpconstcol = NULL;
1430  (*sdpi)->sdpconstval = NULL;
1431  (*sdpi)->sdpnblockvarnonz = NULL;
1432  (*sdpi)->sdpvar = NULL;
1433  (*sdpi)->sdprow = NULL;
1434  (*sdpi)->sdpcol = NULL;
1435  (*sdpi)->sdpval = NULL;
1436  (*sdpi)->lplhs = NULL;
1437  (*sdpi)->lprhs = NULL;
1438  (*sdpi)->lprow = NULL;
1439  (*sdpi)->lpcol = NULL;
1440  (*sdpi)->lpval = NULL;
1441 
1442  (*sdpi)->epsilon = DEFAULT_SDPSOLVEREPSILON;
1443  (*sdpi)->feastol = DEFAULT_SDPSOLVERFEASTOL;
1444  (*sdpi)->penaltyparam = DEFAULT_PENALTYPARAM;
1445  (*sdpi)->penaltyparam = DEFAULT_MAXPENALTYPARAM;
1446  (*sdpi)->bestbound = -SCIPsdpiSolverInfinity((*sdpi)->sdpisolver);
1447  (*sdpi)->primalslater = SCIP_SDPSLATER_NOINFO;
1448  (*sdpi)->dualslater = SCIP_SDPSLATER_NOINFO;
1449 
1450  return SCIP_OKAY;
1451 }
1452 
1454 SCIP_RETCODE SCIPsdpiFree(
1455  SCIP_SDPI** sdpi
1456  )
1457 {
1458  int i;
1459  int j;
1460 
1461  SCIPdebugMessage("Calling SCIPsdpiFree \n");
1462  assert ( sdpi != NULL );
1463  assert ( *sdpi != NULL );
1464 
1465  /* free the LP part */
1466  BMSfreeBlockMemoryArrayNull((*sdpi)->blkmem, &((*sdpi)->lpval), (*sdpi)->lpnnonz);
1467  BMSfreeBlockMemoryArrayNull((*sdpi)->blkmem, &((*sdpi)->lpcol), (*sdpi)->lpnnonz);
1468  BMSfreeBlockMemoryArrayNull((*sdpi)->blkmem, &((*sdpi)->lprow), (*sdpi)->lpnnonz);
1469  BMSfreeBlockMemoryArrayNull((*sdpi)->blkmem, &((*sdpi)->lprhs), (*sdpi)->nlpcons);
1470  BMSfreeBlockMemoryArrayNull((*sdpi)->blkmem, &((*sdpi)->lplhs), (*sdpi)->nlpcons);
1471 
1472  /* free the individual nonzeros */
1473  for (i = 0; i < (*sdpi)->nsdpblocks; i++)
1474  {
1475  for (j = 0; j < (*sdpi)->sdpnblockvars[i]; j++)
1476  {
1477  BMSfreeBlockMemoryArrayNull((*sdpi)->blkmem, &((*sdpi)->sdpval[i][j]), (*sdpi)->sdpnblockvarnonz[i][j]);
1478  BMSfreeBlockMemoryArrayNull((*sdpi)->blkmem, &((*sdpi)->sdprow[i][j]), (*sdpi)->sdpnblockvarnonz[i][j]);
1479  BMSfreeBlockMemoryArrayNull((*sdpi)->blkmem, &((*sdpi)->sdpcol[i][j]), (*sdpi)->sdpnblockvarnonz[i][j]);
1480  }
1481  BMSfreeBlockMemoryArrayNull((*sdpi)->blkmem, &((*sdpi)->sdpval[i]), (*sdpi)->sdpnblockvars[i]);
1482  BMSfreeBlockMemoryArrayNull((*sdpi)->blkmem, &((*sdpi)->sdprow[i]), (*sdpi)->sdpnblockvars[i]);
1483  BMSfreeBlockMemoryArrayNull((*sdpi)->blkmem, &((*sdpi)->sdpcol[i]), (*sdpi)->sdpnblockvars[i]);
1484  BMSfreeBlockMemoryArrayNull((*sdpi)->blkmem, &((*sdpi)->sdpvar[i]), (*sdpi)->sdpnblockvars[i]);
1485  BMSfreeBlockMemoryArrayNull((*sdpi)->blkmem, &((*sdpi)->sdpnblockvarnonz[i]), (*sdpi)->sdpnblockvars[i]);
1486  BMSfreeBlockMemoryArrayNull((*sdpi)->blkmem, &((*sdpi)->sdpconstval[i]), (*sdpi)->sdpconstnblocknonz[i]);
1487  BMSfreeBlockMemoryArrayNull((*sdpi)->blkmem, &((*sdpi)->sdpconstrow[i]), (*sdpi)->sdpconstnblocknonz[i]);
1488  BMSfreeBlockMemoryArrayNull((*sdpi)->blkmem, &((*sdpi)->sdpconstcol[i]), (*sdpi)->sdpconstnblocknonz[i]);
1489  }
1490 
1491  /* free the rest */
1492  BMSfreeBlockMemoryArrayNull((*sdpi)->blkmem, &((*sdpi)->sdpnblockvarnonz), (*sdpi)->nsdpblocks);
1493  BMSfreeBlockMemoryArrayNull((*sdpi)->blkmem, &((*sdpi)->sdpconstnblocknonz), (*sdpi)->nsdpblocks);
1494  BMSfreeBlockMemoryArrayNull((*sdpi)->blkmem, &((*sdpi)->sdpval), (*sdpi)->nsdpblocks);
1495  BMSfreeBlockMemoryArrayNull((*sdpi)->blkmem, &((*sdpi)->sdpcol), (*sdpi)->nsdpblocks);
1496  BMSfreeBlockMemoryArrayNull((*sdpi)->blkmem, &((*sdpi)->sdprow), (*sdpi)->nsdpblocks);
1497  BMSfreeBlockMemoryArrayNull((*sdpi)->blkmem, &((*sdpi)->sdpvar), (*sdpi)->nsdpblocks);
1498  BMSfreeBlockMemoryArrayNull((*sdpi)->blkmem, &((*sdpi)->sdpconstval), (*sdpi)->nsdpblocks);
1499  BMSfreeBlockMemoryArrayNull((*sdpi)->blkmem, &((*sdpi)->sdpconstcol), (*sdpi)->nsdpblocks);
1500  BMSfreeBlockMemoryArrayNull((*sdpi)->blkmem, &((*sdpi)->sdpconstrow), (*sdpi)->nsdpblocks);
1501  BMSfreeBlockMemoryArrayNull((*sdpi)->blkmem, &((*sdpi)->sdpnblockvars), (*sdpi)->nsdpblocks);
1502  BMSfreeBlockMemoryArrayNull((*sdpi)->blkmem, &((*sdpi)->sdpblocksizes), (*sdpi)->nsdpblocks);
1503  BMSfreeBlockMemoryArray((*sdpi)->blkmem, &((*sdpi)->ub), (*sdpi)->nvars);/*lint !e737*/
1504  BMSfreeBlockMemoryArray((*sdpi)->blkmem, &((*sdpi)->lb), (*sdpi)->nvars);/*lint !e737*/
1505  BMSfreeBlockMemoryArray((*sdpi)->blkmem, &((*sdpi)->obj), (*sdpi)->nvars);/*lint !e737*/
1506 
1507  /* free the solver */
1508  SCIP_CALL( SCIPsdpiSolverFree(&((*sdpi)->sdpisolver)) );
1509 
1510  BMSfreeBlockMemory((*sdpi)->blkmem, sdpi);
1511 
1512  return SCIP_OKAY;
1513 }
1514 
1519 SCIP_RETCODE SCIPsdpiClone(
1520  SCIP_SDPI* oldsdpi,
1521  SCIP_SDPI* newsdpi
1522  )
1523 {
1524  BMS_BLKMEM* blkmem;
1525  int nvars;
1526  int nsdpblocks;
1527  int lpnnonz;
1528  int b;
1529  int v;
1530 
1531  assert( oldsdpi != NULL );
1532 
1533  SCIPdebugMessage("Cloning SDPI %d\n", oldsdpi->sdpid);
1534 
1535  /* general data */
1536  blkmem = oldsdpi->blkmem;
1537  nvars = oldsdpi->nvars;
1538  nsdpblocks = oldsdpi->nsdpblocks;
1539  lpnnonz = oldsdpi->lpnnonz;
1540 
1541  BMS_CALL( BMSallocBlockMemory(blkmem, &newsdpi) );
1542 
1543  SCIP_CALL( SCIPsdpiSolverCreate(&(newsdpi->sdpisolver), oldsdpi->messagehdlr, oldsdpi->blkmem) ); /* create new SDP-Solver Interface */
1544 
1545  newsdpi->messagehdlr = oldsdpi->messagehdlr;
1546  newsdpi->blkmem = blkmem;
1547  newsdpi->nvars = nvars;
1548 
1549  BMS_CALL( BMSduplicateBlockMemoryArray(blkmem, &(newsdpi->obj), oldsdpi->obj, nvars) );
1550  BMS_CALL( BMSduplicateBlockMemoryArray(blkmem, &(newsdpi->lb), oldsdpi->lb, nvars) );
1551  BMS_CALL( BMSduplicateBlockMemoryArray(blkmem, &(newsdpi->ub), oldsdpi->ub, nvars) );
1552 
1553  newsdpi->nsdpblocks = nsdpblocks;
1554 
1555  BMS_CALL( BMSduplicateBlockMemoryArray(blkmem, &(newsdpi->sdpblocksizes), oldsdpi->sdpblocksizes, nsdpblocks) );
1556  BMS_CALL( BMSduplicateBlockMemoryArray(blkmem, &(newsdpi->sdpnblockvars), oldsdpi->sdpnblockvars, nsdpblocks) );
1557 
1558  /* constant SDP data */
1559  newsdpi->sdpconstnnonz = oldsdpi->sdpconstnnonz;
1560 
1561  BMS_CALL( BMSduplicateBlockMemoryArray(blkmem, &(newsdpi->sdpconstnblocknonz), oldsdpi->sdpconstnblocknonz, nsdpblocks) );
1562  BMS_CALL( BMSallocBlockMemoryArray(blkmem, &(newsdpi->sdpconstrow), nsdpblocks) );
1563  BMS_CALL( BMSallocBlockMemoryArray(blkmem, &(newsdpi->sdpconstcol), nsdpblocks) );
1564  BMS_CALL( BMSallocBlockMemoryArray(blkmem, &(newsdpi->sdpconstval), nsdpblocks) );
1565 
1566  for (b = 0; b < nsdpblocks; b++)
1567  {
1568  BMS_CALL( BMSduplicateBlockMemoryArray(blkmem, &(newsdpi->sdpconstrow[b]), oldsdpi->sdpconstrow[b], oldsdpi->sdpconstnblocknonz[b]) );
1569  BMS_CALL( BMSduplicateBlockMemoryArray(blkmem, &(newsdpi->sdpconstcol[b]), oldsdpi->sdpconstcol[b], oldsdpi->sdpconstnblocknonz[b]) );
1570  BMS_CALL( BMSduplicateBlockMemoryArray(blkmem, &(newsdpi->sdpconstval[b]), oldsdpi->sdpconstval[b], oldsdpi->sdpconstnblocknonz[b]) );
1571  }
1572 
1573  /* SDP data */
1574  newsdpi->sdpnnonz = oldsdpi->sdpnnonz;
1575 
1576  BMS_CALL( BMSallocBlockMemoryArray(blkmem, &(newsdpi->sdpnblockvarnonz), nsdpblocks) );
1577  BMS_CALL( BMSallocBlockMemoryArray(blkmem, &(newsdpi->sdpvar), nsdpblocks) );
1578  BMS_CALL( BMSallocBlockMemoryArray(blkmem, &(newsdpi->sdprow), nsdpblocks) );
1579  BMS_CALL( BMSallocBlockMemoryArray(blkmem, &(newsdpi->sdpcol), nsdpblocks) );
1580  BMS_CALL( BMSallocBlockMemoryArray(blkmem, &(newsdpi->sdpval), nsdpblocks) );
1581 
1582  for (b = 0; b < nsdpblocks; b++)
1583  {
1584  BMS_CALL( BMSduplicateBlockMemoryArray(blkmem, &(newsdpi->sdpnblockvarnonz[b]), oldsdpi->sdpnblockvarnonz[b], oldsdpi->sdpnblockvars[b]) );
1585  BMS_CALL( BMSduplicateBlockMemoryArray(blkmem, &(newsdpi->sdpvar[b]), oldsdpi->sdpvar[b], oldsdpi->sdpnblockvars[b]) );
1586 
1587  BMS_CALL( BMSallocBlockMemoryArray(blkmem, &(newsdpi->sdprow[b]), oldsdpi->sdpnblockvars[b]) );
1588  BMS_CALL( BMSallocBlockMemoryArray(blkmem, &(newsdpi->sdpcol[b]), oldsdpi->sdpnblockvars[b]) );
1589  BMS_CALL( BMSallocBlockMemoryArray(blkmem, &(newsdpi->sdpval[b]), oldsdpi->sdpnblockvars[b]) );
1590 
1591  for (v = 0; v < oldsdpi->sdpnblockvars[b]; v++)
1592  {
1593  BMS_CALL( BMSduplicateBlockMemoryArray(blkmem, &(newsdpi->sdprow[b][v]), oldsdpi->sdprow[b][v], oldsdpi->sdpnblockvarnonz[b][v]) );
1594  BMS_CALL( BMSduplicateBlockMemoryArray(blkmem, &(newsdpi->sdpcol[b][v]), oldsdpi->sdpcol[b][v], oldsdpi->sdpnblockvarnonz[b][v]) );
1595  BMS_CALL( BMSduplicateBlockMemoryArray(blkmem, &(newsdpi->sdpval[b][v]), oldsdpi->sdpval[b][v], oldsdpi->sdpnblockvarnonz[b][v]) );
1596  }
1597  }
1598 
1599  /* LP data */
1600  newsdpi->nlpcons = oldsdpi->nlpcons;
1601 
1602  BMS_CALL( BMSduplicateBlockMemoryArray(blkmem, &(newsdpi->lplhs), oldsdpi->lplhs, oldsdpi->nlpcons) );
1603  BMS_CALL( BMSduplicateBlockMemoryArray(blkmem, &(newsdpi->lprhs), oldsdpi->lprhs, oldsdpi->nlpcons) );
1604 
1605  newsdpi->lpnnonz = lpnnonz;
1606 
1607  BMS_CALL( BMSduplicateBlockMemoryArray(blkmem, &(newsdpi->lprow), oldsdpi->lprow, lpnnonz) );
1608  BMS_CALL( BMSduplicateBlockMemoryArray(blkmem, &(newsdpi->lpcol), oldsdpi->lpcol, lpnnonz) );
1609  BMS_CALL( BMSduplicateBlockMemoryArray(blkmem, &(newsdpi->lpval), oldsdpi->lpval, lpnnonz) );
1610 
1611  /* other data */
1612  newsdpi->solved = FALSE; /* as we don't copy the sdpisolver, this needs to be set to false */
1613  newsdpi->penalty = FALSE; /* all things about SDP-solutions are set to false as well, as we didn't solve the problem */
1614  newsdpi->infeasible = FALSE;
1615  newsdpi->allfixed = FALSE;
1616  newsdpi->sdpid = 1000000 + oldsdpi->sdpid; /* this is only used for debug output, setting it to this value should make it clear, that it is a new sdpi */
1617  newsdpi->epsilon = oldsdpi->epsilon;
1618  newsdpi->feastol = oldsdpi->feastol;
1619 
1620  return SCIP_OKAY;
1621 }
1622 
1626 /*
1627  * Modification Methods
1628  */
1629 
1638 SCIP_RETCODE SCIPsdpiLoadSDP(
1639  SCIP_SDPI* sdpi,
1640  int nvars,
1641  SCIP_Real* obj,
1642  SCIP_Real* lb,
1643  SCIP_Real* ub,
1644  int nsdpblocks,
1645  int* sdpblocksizes,
1646  int* sdpnblockvars,
1647  int sdpconstnnonz,
1648  int* sdpconstnblocknonz,
1650  int** sdpconstrow,
1651  int** sdpconstcol,
1652  SCIP_Real** sdpconstval,
1653  int sdpnnonz,
1654  int** sdpnblockvarnonz,
1656  int** sdpvar,
1658  int*** sdprow,
1661  int*** sdpcol,
1662  SCIP_Real*** sdpval,
1664  int nlpcons,
1665  SCIP_Real* lplhs,
1666  SCIP_Real* lprhs,
1667  int lpnnonz,
1668  int* lprow,
1669  int* lpcol,
1670  SCIP_Real* lpval
1671  )
1672 {
1673  int i;
1674  int v;
1675  int block;
1676 
1677  SCIPdebugMessage("Calling SCIPsdpiLoadSDP (%d)\n",sdpi->sdpid);
1678 
1679  assert ( sdpi != NULL );
1680  assert ( nvars > 0 );
1681  assert ( obj != NULL );
1682  assert ( lb != NULL );
1683  assert ( ub != NULL );
1684 
1685 #ifdef SCIP_DEBUG
1686  if (sdpconstnnonz > 0 || sdpnnonz > 0 || nsdpblocks > 0)
1687  {
1688  assert ( sdpblocksizes != NULL );
1689  assert ( sdpnblockvars != NULL );
1690  assert ( nsdpblocks > 0 );
1691  assert ( sdpconstnblocknonz != NULL );
1692  assert ( sdpnblockvarnonz != NULL );
1693 
1694  if (sdpconstnnonz > 0)
1695  {
1696  assert ( sdpconstrow != NULL );
1697  assert ( sdpconstcol != NULL );
1698  assert ( sdpconstval != NULL );
1699 
1700  for (i = 0; i < nsdpblocks; i++)
1701  {
1702  if (sdpconstnblocknonz[i] > 0)
1703  {
1704  assert ( sdpconstrow[i] != NULL );
1705  assert ( sdpconstcol[i] != NULL );
1706  assert ( sdpconstval[i] != NULL );
1707  }
1708  }
1709  }
1710 
1711  if (sdpnnonz > 0)
1712  {
1713  assert ( sdprow != NULL );
1714  assert ( sdpcol != NULL );
1715  assert ( sdpval != NULL );
1716 
1717  for ( i = 0; i < nsdpblocks; i++ )
1718  {
1719  assert ( sdpcol[i] != NULL );
1720  assert ( sdprow[i] != NULL );
1721  assert ( sdpval[i] != NULL );
1722 
1723  for ( v = 0; v < sdpnblockvars[i]; v++)
1724  {
1725  if (sdpnblockvarnonz[i][v] > 0)
1726  {
1727  assert ( sdpcol[i][v] != NULL );
1728  assert ( sdprow[i][v] != NULL );
1729  assert ( sdpval[i][v] != NULL );
1730  }
1731  }
1732  }
1733  }
1734  }
1735 #endif
1736 
1737  assert ( nlpcons == 0 || lplhs != NULL );
1738  assert ( nlpcons == 0 || lprhs != NULL );
1739  assert ( lpnnonz == 0 || lprow != NULL );
1740  assert ( lpnnonz == 0 || lpcol != NULL );
1741  assert ( lpnnonz == 0 || lpval != NULL );
1742 
1743  /* memory allocation */
1744 
1745  /* first free the old arrays */
1746  for (block = sdpi->nsdpblocks - 1; block >= 0; block--)
1747  {
1748  for (v = sdpi->sdpnblockvars[block] - 1; v >= 0; v--)
1749  {
1750  BMSfreeBlockMemoryArrayNull(sdpi->blkmem, &(sdpi->sdpval[block][v]), sdpi->sdpnblockvarnonz[block][v]);
1751  BMSfreeBlockMemoryArrayNull(sdpi->blkmem, &(sdpi->sdprow[block][v]), sdpi->sdpnblockvarnonz[block][v]);
1752  BMSfreeBlockMemoryArrayNull(sdpi->blkmem, &(sdpi->sdpcol[block][v]), sdpi->sdpnblockvarnonz[block][v]);
1753  }
1754 
1755  BMSfreeBlockMemoryArrayNull(sdpi->blkmem, &(sdpi->sdpval[block]), sdpi->sdpnblockvars[block]);
1756  BMSfreeBlockMemoryArrayNull(sdpi->blkmem, &(sdpi->sdprow[block]), sdpi->sdpnblockvars[block]);
1757  BMSfreeBlockMemoryArrayNull(sdpi->blkmem, &(sdpi->sdpcol[block]), sdpi->sdpnblockvars[block]);
1758  BMSfreeBlockMemoryArrayNull(sdpi->blkmem, &(sdpi->sdpconstval[block]), sdpi->sdpconstnblocknonz[block]);
1759  BMSfreeBlockMemoryArrayNull(sdpi->blkmem, &(sdpi->sdpconstrow[block]), sdpi->sdpconstnblocknonz[block]);
1760  BMSfreeBlockMemoryArrayNull(sdpi->blkmem, &(sdpi->sdpconstcol[block]), sdpi->sdpconstnblocknonz[block]);
1761  BMSfreeBlockMemoryArrayNull(sdpi->blkmem, &(sdpi->sdpnblockvarnonz[block]), sdpi->sdpnblockvars[block]);
1762  BMSfreeBlockMemoryArrayNull(sdpi->blkmem, &(sdpi->sdpvar[block]), sdpi->sdpnblockvars[block]);
1763  }
1764 
1765  BMSfreeBlockMemoryArrayNull(sdpi->blkmem, &(sdpi->ub), sdpi->nvars);
1766  BMSfreeBlockMemoryArrayNull(sdpi->blkmem, &(sdpi->lb), sdpi->nvars);
1767  BMSfreeBlockMemoryArrayNull(sdpi->blkmem, &(sdpi->obj), sdpi->nvars);
1768 
1769  BMSfreeBlockMemoryArrayNull(sdpi->blkmem, &(sdpi->sdpblocksizes), sdpi->nsdpblocks);
1770  BMSfreeBlockMemoryArrayNull(sdpi->blkmem, &(sdpi->sdpnblockvars), sdpi->nsdpblocks);
1771  BMSfreeBlockMemoryArrayNull(sdpi->blkmem, &(sdpi->sdpconstnblocknonz), sdpi->nsdpblocks);
1772 
1773  /* duplicate some arrays */
1774  BMS_CALL( BMSduplicateBlockMemoryArray(sdpi->blkmem, &(sdpi->obj), obj, nvars) );
1775  BMS_CALL( BMSduplicateBlockMemoryArray(sdpi->blkmem, &(sdpi->lb), lb, nvars) );
1776  BMS_CALL( BMSduplicateBlockMemoryArray(sdpi->blkmem, &(sdpi->ub), ub, nvars) );
1777  DUPLICATE_ARRAY_NULL(sdpi->blkmem, &(sdpi->sdpblocksizes), sdpblocksizes, nsdpblocks);
1778  DUPLICATE_ARRAY_NULL(sdpi->blkmem, &(sdpi->sdpnblockvars), sdpnblockvars, nsdpblocks);
1779  DUPLICATE_ARRAY_NULL(sdpi->blkmem, &(sdpi->sdpconstnblocknonz), sdpconstnblocknonz, nsdpblocks);
1780 
1781  /* allocate memory for the sdp arrays & duplicate them */
1782  BMS_CALL( BMSreallocBlockMemoryArray(sdpi->blkmem, &(sdpi->sdpnblockvarnonz), sdpi->nsdpblocks, nsdpblocks) );
1783  BMS_CALL( BMSreallocBlockMemoryArray(sdpi->blkmem, &(sdpi->sdpconstcol), sdpi->nsdpblocks, nsdpblocks) );
1784  BMS_CALL( BMSreallocBlockMemoryArray(sdpi->blkmem, &(sdpi->sdpconstrow), sdpi->nsdpblocks, nsdpblocks) );
1785  BMS_CALL( BMSreallocBlockMemoryArray(sdpi->blkmem, &(sdpi->sdpconstval), sdpi->nsdpblocks, nsdpblocks) );
1786  BMS_CALL( BMSreallocBlockMemoryArray(sdpi->blkmem, &(sdpi->sdpvar), sdpi->nsdpblocks, nsdpblocks) );
1787  BMS_CALL( BMSreallocBlockMemoryArray(sdpi->blkmem, &(sdpi->sdpcol), sdpi->nsdpblocks, nsdpblocks) );
1788  BMS_CALL( BMSreallocBlockMemoryArray(sdpi->blkmem, &(sdpi->sdprow), sdpi->nsdpblocks, nsdpblocks) );
1789  BMS_CALL( BMSreallocBlockMemoryArray(sdpi->blkmem, &(sdpi->sdpval), sdpi->nsdpblocks, nsdpblocks) );
1790 
1791  for (block = 0; block < nsdpblocks; block++)
1792  {
1793  DUPLICATE_ARRAY_NULL(sdpi->blkmem, &(sdpi->sdpnblockvarnonz[block]), sdpnblockvarnonz[block], sdpnblockvars[block]);
1794 
1795  DUPLICATE_ARRAY_NULL(sdpi->blkmem, &(sdpi->sdpconstcol[block]), sdpconstcol[block], sdpconstnblocknonz[block]);
1796  DUPLICATE_ARRAY_NULL(sdpi->blkmem, &(sdpi->sdpconstrow[block]), sdpconstrow[block], sdpconstnblocknonz[block]);
1797  DUPLICATE_ARRAY_NULL(sdpi->blkmem, &(sdpi->sdpconstval[block]), sdpconstval[block], sdpconstnblocknonz[block]);
1798 
1799  /* make sure that we have a lower triangular matrix */
1800  for (i = 0; i < sdpi->sdpconstnblocknonz[block]; ++i)
1801  ensureLowerTriangular(&(sdpconstrow[block][i]), &(sdpconstcol[block][i]));
1802 
1803  DUPLICATE_ARRAY_NULL(sdpi->blkmem, &(sdpi->sdpvar[block]), sdpvar[block], sdpnblockvars[block]);
1804 
1805  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &(sdpi->sdpcol[block]), sdpnblockvars[block]) );
1806  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &(sdpi->sdprow[block]), sdpnblockvars[block]) );
1807  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &(sdpi->sdpval[block]), sdpnblockvars[block]) );
1808 
1809  for (v = 0; v < sdpi->sdpnblockvars[block]; v++)
1810  {
1811  DUPLICATE_ARRAY_NULL(sdpi->blkmem, &(sdpi->sdpcol[block][v]), sdpcol[block][v], sdpnblockvarnonz[block][v]);
1812  DUPLICATE_ARRAY_NULL(sdpi->blkmem, &(sdpi->sdprow[block][v]), sdprow[block][v], sdpnblockvarnonz[block][v]);
1813  DUPLICATE_ARRAY_NULL(sdpi->blkmem, &(sdpi->sdpval[block][v]), sdpval[block][v], sdpnblockvarnonz[block][v]);
1814 
1815  /* make sure that we have a lower triangular matrix */
1816  for (i = 0; i < sdpi->sdpnblockvarnonz[block][v]; ++i)
1817  ensureLowerTriangular(&(sdprow[block][v][i]), &(sdpcol[block][v][i]));
1818  }
1819  }
1820 
1821  /* free old and duplicate new arrays for the LP part */
1822  BMSfreeBlockMemoryArrayNull(sdpi->blkmem, &(sdpi->lpval), sdpi->lpnnonz);
1823  BMSfreeBlockMemoryArrayNull(sdpi->blkmem, &(sdpi->lpcol), sdpi->lpnnonz);
1824  BMSfreeBlockMemoryArrayNull(sdpi->blkmem, &(sdpi->lprow), sdpi->lpnnonz);
1825  BMSfreeBlockMemoryArrayNull(sdpi->blkmem, &(sdpi->lprhs), sdpi->nlpcons);
1826  BMSfreeBlockMemoryArrayNull(sdpi->blkmem, &(sdpi->lplhs), sdpi->nlpcons);
1827 
1828  DUPLICATE_ARRAY_NULL(sdpi->blkmem, &(sdpi->lplhs), lplhs, nlpcons);
1829  DUPLICATE_ARRAY_NULL(sdpi->blkmem, &(sdpi->lprhs), lprhs, nlpcons);
1830  DUPLICATE_ARRAY_NULL(sdpi->blkmem, &(sdpi->lprow), lprow, lpnnonz);
1831  DUPLICATE_ARRAY_NULL(sdpi->blkmem, &(sdpi->lpcol), lpcol, lpnnonz);
1832  DUPLICATE_ARRAY_NULL(sdpi->blkmem, &(sdpi->lpval), lpval, lpnnonz);
1833 
1834  /* set the general information */
1835  sdpi->nvars = nvars;
1836  sdpi->nsdpblocks = nsdpblocks;
1837 
1838  sdpi->sdpconstnnonz = sdpconstnnonz;
1839  sdpi->sdpnnonz = sdpnnonz;
1840 
1841  /* LP part */
1842  sdpi->lpnnonz = lpnnonz;
1843  sdpi->nlpcons = nlpcons;
1844 
1845  sdpi->solved = FALSE;
1846  sdpi->infeasible = FALSE;
1847  sdpi->allfixed = FALSE;
1848  sdpi->nsdpcalls = 0;
1849  sdpi->niterations = 0;
1850 
1851  return SCIP_OKAY;
1852 }
1853 
1858 SCIP_RETCODE SCIPsdpiAddLPRows(
1859  SCIP_SDPI* sdpi,
1860  int nrows,
1861  const SCIP_Real* lhs,
1862  const SCIP_Real* rhs,
1863  int nnonz,
1864  const int* row,
1866  const int* col,
1867  const SCIP_Real* val
1868  )
1869 {
1870  int i;
1871 
1872  SCIPdebugMessage("Adding %d LP-Constraints to SDP %d.\n", nrows, sdpi->sdpid);
1873 
1874  assert ( sdpi != NULL );
1875 
1876  if ( nrows == 0 )
1877  return SCIP_OKAY; /* nothing to do in this case */
1878 
1879  assert ( lhs != NULL );
1880  assert ( rhs != NULL );
1881  assert ( nnonz >= 0 );
1882  assert ( row != NULL );
1883  assert ( col != NULL );
1884  assert ( val != NULL );
1885 
1886  BMS_CALL( BMSreallocBlockMemoryArray(sdpi->blkmem, &(sdpi->lplhs), sdpi->nlpcons, sdpi->nlpcons + nrows) ); /*lint !e776*/
1887  BMS_CALL( BMSreallocBlockMemoryArray(sdpi->blkmem, &(sdpi->lprhs), sdpi->nlpcons, sdpi->nlpcons + nrows) ); /*lint !e776*/
1888 
1889  for (i = 0; i < nrows; i++)
1890  {
1891  sdpi->lplhs[sdpi->nlpcons + i] = lhs[i]; /*lint !e679*/
1892  sdpi->lprhs[sdpi->nlpcons + i] = rhs[i]; /*lint !e679*/
1893  }
1894 
1895  BMS_CALL( BMSreallocBlockMemoryArray(sdpi->blkmem, &(sdpi->lprow), sdpi->lpnnonz, sdpi->lpnnonz + nnonz) ); /*lint !e776*/
1896  BMS_CALL( BMSreallocBlockMemoryArray(sdpi->blkmem, &(sdpi->lpcol), sdpi->lpnnonz, sdpi->lpnnonz + nnonz) ); /*lint !e776*/
1897  BMS_CALL( BMSreallocBlockMemoryArray(sdpi->blkmem, &(sdpi->lpval), sdpi->lpnnonz, sdpi->lpnnonz + nnonz) ); /*lint !e776*/
1898 
1899  for (i = 0; i < nnonz; i++)
1900  {
1901  assert ( 0 <= row[i] && row[i] < nrows );
1902  /* the new rows are added at the end, so the row indices are increased by the old number of LP-constraints */
1903  sdpi->lprow[sdpi->lpnnonz + i] = row[i] + sdpi->nlpcons; /*lint !e679*/
1904 
1905  assert ( 0 <= col[i] && col[i] < sdpi->nvars ); /* only existing vars should be added to the LP-constraints */
1906  sdpi->lpcol[sdpi->lpnnonz + i] = col[i]; /*lint !e679*/
1907 
1908  sdpi->lpval[sdpi->lpnnonz + i] = val[i]; /*lint !e679*/
1909  }
1910 
1911  sdpi->nlpcons = sdpi->nlpcons + nrows;
1912  sdpi->lpnnonz = sdpi->lpnnonz + nnonz;
1913 
1914  sdpi->solved = FALSE;
1915  sdpi->infeasible = FALSE;
1916  sdpi->nsdpcalls = 0;
1917  sdpi->niterations = 0;
1918 
1919  return SCIP_OKAY;
1920 }
1921 
1923 SCIP_RETCODE SCIPsdpiDelLPRows(
1924  SCIP_SDPI* sdpi,
1925  int firstrow,
1926  int lastrow
1927  )
1928 {
1929  int i;
1930  int deletedrows;
1931  int firstrowind;
1932  int lastrowind;
1933  int deletednonz;
1934 
1935  SCIPdebugMessage("Deleting rows %d to %d from SDP %d.\n", firstrow, lastrow, sdpi->sdpid);
1936 
1937  assert ( sdpi != NULL );
1938  assert ( firstrow >= 0 );
1939  assert ( firstrow <= lastrow );
1940  assert ( lastrow < sdpi->nlpcons );
1941 
1942  /* shorten the procedure if the whole LP-part is to be deleted */
1943  if (firstrow == 0 && lastrow == sdpi->nlpcons - 1)
1944  {
1945  BMSfreeBlockMemoryArray(sdpi->blkmem, &(sdpi->lpval), sdpi->lpnnonz);/*lint !e737*/
1946  BMSfreeBlockMemoryArray(sdpi->blkmem, &(sdpi->lprow), sdpi->lpnnonz);/*lint !e737*/
1947  BMSfreeBlockMemoryArray(sdpi->blkmem, &(sdpi->lpcol), sdpi->lpnnonz);/*lint !e737*/
1948  BMSfreeBlockMemoryArray(sdpi->blkmem, &(sdpi->lprhs), sdpi->nlpcons);/*lint !e737*/
1949  BMSfreeBlockMemoryArray(sdpi->blkmem, &(sdpi->lplhs), sdpi->nlpcons);/*lint !e737*/
1950 
1951  sdpi->lplhs = NULL;
1952  sdpi->lprhs = NULL;
1953  sdpi->lpcol = NULL;
1954  sdpi->lprow = NULL;
1955  sdpi->lpval = NULL;
1956 
1957  sdpi->nlpcons = 0;
1958  sdpi->lpnnonz = 0;
1959 
1960  sdpi->solved = FALSE;
1961  sdpi->infeasible = FALSE;
1962  sdpi->allfixed = FALSE;
1963  sdpi->nsdpcalls = 0;
1964  sdpi->niterations = 0;
1965 
1966  return SCIP_OKAY;
1967  }
1968 
1969  deletedrows = lastrow - firstrow + 1; /*lint !e834*/
1970  deletednonz = 0;
1971 
1972  /* first delete the left- and right-hand-sides */
1973  for (i = lastrow + 1; i < sdpi->nlpcons; i++) /* shift all rhs after the deleted rows */
1974  {
1975  sdpi->lplhs[i - deletedrows] = sdpi->lplhs[i]; /*lint !e679*/
1976  sdpi->lprhs[i - deletedrows] = sdpi->lprhs[i]; /*lint !e679*/
1977  }
1978  BMS_CALL( BMSreallocBlockMemoryArray(sdpi->blkmem, &(sdpi->lplhs), sdpi->nlpcons, sdpi->nlpcons - deletedrows) ); /*lint !e776*/
1979  BMS_CALL( BMSreallocBlockMemoryArray(sdpi->blkmem, &(sdpi->lprhs), sdpi->nlpcons, sdpi->nlpcons - deletedrows) ); /*lint !e776*/
1980 
1981  /* for deleting and reordering the lpnonzeroes, the arrays first have to be sorted to have the rows to be deleted together */
1982  SCIPsortIntIntReal(sdpi->lprow, sdpi->lpcol, sdpi->lpval, sdpi->lpnnonz); /* sort all arrays by non-decreasing row indices */
1983 
1984  firstrowind = -1;
1985  /*iterate over the lprowind array to find the first index belonging to a row that should be deleted */
1986  for (i = 0; i < sdpi->lpnnonz; i++)
1987  {
1988  if (sdpi->lprow[i] >= firstrow && sdpi->lprow[i] <= lastrow) /* the and part makes sure that there actually were some nonzeroes in these rows */
1989  {
1990  firstrowind = i;
1991  lastrowind = i;
1992  i++;
1993  break;
1994  }
1995  }
1996 
1997  if (firstrowind > -1) /* if this is still 0 there are no nonzeroes for the given rows */
1998  {
1999  /* now find the last occurence of one of the rows (as these are sorted all in between also belong to deleted rows and will be removed) */
2000  while (i < sdpi->lpnnonz && sdpi->lprow[i] <= lastrow)
2001  {
2002  lastrowind++; /*lint !e644*/
2003  i++;
2004  }
2005  deletednonz = lastrowind - firstrowind + 1; /*lint !e834*/
2006 
2007  /* finally shift all LP-array-entries after the deleted rows */
2008  for (i = lastrowind + 1; i < sdpi->lpnnonz; i++)
2009  {
2010  sdpi->lpcol[i - deletednonz] = sdpi->lpcol[i]; /*lint !e679*/
2011  /* all rowindices after the deleted ones have to be lowered to still have ongoing indices from 0 to nlpcons-1 */
2012  sdpi->lprow[i - deletednonz] = sdpi->lprow[i] - deletedrows; /*lint !e679*/
2013  sdpi->lpval[i - deletednonz] = sdpi->lpval[i]; /*lint !e679*/
2014  }
2015  }
2016 
2017  BMS_CALL( BMSreallocBlockMemoryArray(sdpi->blkmem, &(sdpi->lpcol), sdpi->lpnnonz, sdpi->lpnnonz - deletednonz) ); /*lint !e776*/
2018  BMS_CALL( BMSreallocBlockMemoryArray(sdpi->blkmem, &(sdpi->lprow), sdpi->lpnnonz, sdpi->lpnnonz - deletednonz) ); /*lint !e776*/
2019  BMS_CALL( BMSreallocBlockMemoryArray(sdpi->blkmem, &(sdpi->lpval), sdpi->lpnnonz, sdpi->lpnnonz - deletednonz) ); /*lint !e776*/
2020  sdpi->nlpcons = sdpi->nlpcons - deletedrows;
2021  sdpi->lpnnonz = sdpi->lpnnonz - deletednonz;
2022 
2023  sdpi->solved = FALSE;
2024  sdpi->infeasible = FALSE;
2025  sdpi->allfixed = FALSE;
2026  sdpi->nsdpcalls = 0;
2027  sdpi->niterations = 0;
2028 
2029  return SCIP_OKAY;
2030 }
2031 
2033 SCIP_RETCODE SCIPsdpiDelLPRowset(
2034  SCIP_SDPI* sdpi,
2035  int* dstat
2038  )
2039 {
2040  int i;
2041  int oldnlpcons;
2042  int deletedrows;
2043 
2044  SCIPdebugMessage("Calling SCIPsdpiDelLPRowset for SDP %d.\n", sdpi->sdpid);
2045 
2046  assert ( sdpi != NULL );
2047  assert ( dstat != NULL );
2048 
2049  oldnlpcons = sdpi->nlpcons;
2050  deletedrows = 0;
2051 
2052  for (i = 0; i < oldnlpcons; i++)
2053  {
2054  if (dstat[i] == 1)
2055  {
2056  /* delete this row, it is shifted by - deletedrows, because in this problem the earlier rows have already been deleted */
2057  SCIP_CALL( SCIPsdpiDelLPRows(sdpi, i - deletedrows, i - deletedrows) );
2058  dstat[i] = -1;
2059  deletedrows++;
2060  }
2061  else
2062  dstat[i] = i - deletedrows;
2063  }
2064 
2065  sdpi->solved = FALSE;
2066  sdpi->infeasible = FALSE;
2067  sdpi->allfixed = FALSE;
2068  sdpi->nsdpcalls = 0;
2069  sdpi->niterations = 0;
2070 
2071  return SCIP_OKAY;
2072 }
2073 
2075 SCIP_RETCODE SCIPsdpiClear(
2076  SCIP_SDPI* sdpi
2077  )
2078 {
2079  assert( sdpi != NULL );
2080 
2081  SCIPdebugMessage("Called SCIPsdpiClear in SDP %d.\n", sdpi->sdpid);
2082 
2083  /* we reset all counters */
2084  sdpi->sdpid = 1;
2085  SCIP_CALL( SCIPsdpiSolverResetCounter(sdpi->sdpisolver) );
2086 
2087  return SCIP_OKAY;
2088 }
2089 
2091 SCIP_RETCODE SCIPsdpiChgObj(
2092  SCIP_SDPI* sdpi,
2093  int nvars,
2094  const int* ind,
2095  const SCIP_Real* obj
2096  )
2097 {
2098  int i;
2099 
2100  SCIPdebugMessage("Changing %d objective coefficients in SDP %d\n", nvars, sdpi->sdpid);
2101 
2102  assert( sdpi != NULL );
2103  assert( ind != NULL );
2104  assert( obj != NULL );
2105 
2106  for (i = 0; i < nvars; i++)
2107  {
2108  assert( 0 <= ind[i] && ind[i] < sdpi->nvars );
2109  sdpi->obj[ind[i]] = obj[i];
2110  }
2111 
2112  sdpi->solved = FALSE;
2113  sdpi->nsdpcalls = 0;
2114  sdpi->niterations = 0;
2115 
2116  return SCIP_OKAY;
2117 }
2118 
2120 SCIP_RETCODE SCIPsdpiChgBounds(
2121  SCIP_SDPI* sdpi,
2122  int nvars,
2123  const int* ind,
2124  const SCIP_Real* lb,
2125  const SCIP_Real* ub
2126  )
2127 {
2128  int i;
2129 
2130  SCIPdebugMessage("Changing %d variable bounds in SDP %d\n", nvars, sdpi->sdpid);
2131 
2132  assert( sdpi != NULL );
2133  assert( ind != NULL );
2134  assert( lb != NULL );
2135  assert( ub != NULL );
2136 
2137  for (i = 0; i < nvars; i++)
2138  {
2139  assert( 0 <= ind[i] && ind[i] < sdpi->nvars );
2140  sdpi->lb[ind[i]] = lb[i];
2141  sdpi->ub[ind[i]] = ub[i];
2142  }
2143 
2144  sdpi->solved = FALSE;
2145  sdpi->infeasible = FALSE;
2146  sdpi->allfixed = FALSE;
2147  sdpi->nsdpcalls = 0;
2148  sdpi->niterations = 0;
2149 
2150  return SCIP_OKAY;
2151 }
2152 
2155  SCIP_SDPI* sdpi,
2156  int nrows,
2157  const int* ind,
2158  const SCIP_Real* lhs,
2159  const SCIP_Real* rhs
2160  )
2161 {
2162  int i;
2163 
2164  SCIPdebugMessage("Changing %d left and right hand sides of SDP %d\n", nrows, sdpi->sdpid);
2165 
2166  assert( sdpi != NULL );
2167  assert( 0 <= nrows && nrows <= sdpi->nlpcons );
2168  assert( ind != NULL );
2169  assert( lhs != NULL );
2170  assert( rhs != NULL );
2171 
2172  for (i = 0; i < nrows; i++)
2173  {
2174  assert ( ind[i] >= 0 );
2175  assert ( ind[i] < sdpi->nlpcons );
2176  sdpi->lplhs[ind[i]] = lhs[i];
2177  sdpi->lprhs[ind[i]] = rhs[i];
2178  }
2179 
2180  sdpi->solved = FALSE;
2181  sdpi->infeasible = FALSE;
2182  sdpi->allfixed = FALSE;
2183  sdpi->nsdpcalls = 0;
2184  sdpi->niterations = 0;
2185 
2186  return SCIP_OKAY;
2187 }
2188 
2189 
2190 /*
2191  * Data Accessing Methods
2192  */
2193 
2198 SCIP_RETCODE SCIPsdpiGetNLPRows(
2199  SCIP_SDPI* sdpi,
2200  int* nlprows
2201  )
2202 {
2203  assert( sdpi != NULL );
2204  assert( nlprows != NULL );
2205 
2206  *nlprows = sdpi->nlpcons;
2207 
2208  return SCIP_OKAY;
2209 }
2210 
2213  SCIP_SDPI* sdpi,
2214  int* nsdpblocks
2215  )
2216 {
2217  assert( sdpi != NULL );
2218  assert( nsdpblocks != NULL );
2219 
2220  *nsdpblocks = sdpi->nsdpblocks;
2221 
2222  return SCIP_OKAY;
2223 }
2224 
2226 SCIP_RETCODE SCIPsdpiGetNVars(
2227  SCIP_SDPI* sdpi,
2228  int* nvars
2229  )
2230 {
2231  assert( sdpi != NULL );
2232  assert( nvars != NULL );
2233 
2234  *nvars = sdpi->nvars;
2235 
2236  return SCIP_OKAY;
2237 }
2238 
2240 SCIP_RETCODE SCIPsdpiGetSDPNNonz(
2241  SCIP_SDPI* sdpi,
2242  int* nnonz
2243  )
2244 {
2245  assert( sdpi != NULL );
2246  assert( nnonz != NULL );
2247 
2248  *nnonz = sdpi->sdpnnonz;
2249 
2250  return SCIP_OKAY;
2251 }
2252 
2255  SCIP_SDPI* sdpi,
2256  int* nnonz
2257  )
2258 {
2259  assert( sdpi != NULL );
2260  assert( nnonz != NULL );
2261 
2262  *nnonz = sdpi->sdpconstnnonz;
2263 
2264  return SCIP_OKAY;
2265 }
2266 
2268 SCIP_RETCODE SCIPsdpiGetLPNNonz(
2269  SCIP_SDPI* sdpi,
2270  int* nnonz
2271  )
2272 {
2273  assert( sdpi != NULL );
2274  assert( nnonz != NULL );
2275 
2276  *nnonz = sdpi->lpnnonz;
2277 
2278  return SCIP_OKAY;
2279 }
2280 
2282 SCIP_RETCODE SCIPsdpiGetObj(
2283  SCIP_SDPI* sdpi,
2284  int firstvar,
2285  int lastvar,
2286  SCIP_Real* vals
2287  )
2288 {
2289  int i;
2290 
2291  assert( sdpi != NULL );
2292  assert( firstvar >= 0 );
2293  assert( firstvar <= lastvar );
2294  assert( lastvar < sdpi->nvars);
2295  assert( vals != NULL );
2296 
2297  for (i = 0; i < lastvar - firstvar + 1; i++) /*lint !e834*/
2298  vals[i] = sdpi->obj[firstvar + i]; /*lint !e679*/
2299 
2300  return SCIP_OKAY;
2301 }
2302 
2304 SCIP_RETCODE SCIPsdpiGetBounds(
2305  SCIP_SDPI* sdpi,
2306  int firstvar,
2307  int lastvar,
2308  SCIP_Real* lbs,
2309  SCIP_Real* ubs
2310  )
2311 {
2312  int i;
2313 
2314  assert( sdpi != NULL );
2315  assert( firstvar >= 0 );
2316  assert( firstvar <= lastvar );
2317  assert( lastvar < sdpi->nvars);
2318  assert( lbs != NULL );
2319  assert( ubs != NULL );
2320 
2321  for (i = 0; i < lastvar - firstvar + 1; i++) /*lint !e834*/
2322  {
2323  if (lbs != NULL)
2324  lbs[i] = sdpi->lb[firstvar + i]; /*lint !e679*/
2325  if (ubs != NULL)
2326  ubs[i] = sdpi->ub[firstvar + i]; /*lint !e679*/
2327  }
2328  return SCIP_OKAY;
2329 }
2330 
2332 SCIP_RETCODE SCIPsdpiGetLhSides(
2333  SCIP_SDPI* sdpi,
2334  int firstrow,
2335  int lastrow,
2336  SCIP_Real* lhss
2337  )
2338 {
2339  int i;
2340 
2341  assert( sdpi != NULL );
2342  assert( firstrow >= 0 );
2343  assert( firstrow <= lastrow );
2344  assert( lastrow < sdpi->nlpcons);
2345  assert( lhss != NULL );
2346 
2347  for (i = 0; i < lastrow - firstrow + 1; i++) /*lint !e834*/
2348  lhss[firstrow + i] = sdpi->lplhs[i]; /*lint !e679*/
2349 
2350  return SCIP_OKAY;
2351 }
2352 
2354 SCIP_RETCODE SCIPsdpiGetRhSides(
2355  SCIP_SDPI* sdpi,
2356  int firstrow,
2357  int lastrow,
2358  SCIP_Real* rhss
2359  )
2360 {
2361  int i;
2362 
2363  assert( sdpi != NULL );
2364  assert( firstrow >= 0 );
2365  assert( firstrow <= lastrow );
2366  assert( lastrow < sdpi->nlpcons);
2367  assert( rhss != NULL );
2368 
2369  for (i = 0; i < lastrow - firstrow + 1; i++) /*lint !e834*/
2370  rhss[firstrow + i] = sdpi->lprhs[i]; /*lint !e679*/
2371 
2372  return SCIP_OKAY;
2373 }
2374 
2375 
2380 /*
2381  * Solving Methods
2382  */
2383 
2388 SCIP_RETCODE SCIPsdpiSolve(
2389  SCIP_SDPI* sdpi,
2390  SCIP_Real* start,
2391  SCIP_SDPSOLVERSETTING startsettings,
2393  SCIP_Bool enforceslatercheck,
2395  SCIP_Real timelimit
2396  )
2397 {
2398  int* sdpconstnblocknonz = NULL;
2399  int** sdpconstrow = NULL;
2400  int** sdpconstcol = NULL;
2401  SCIP_Real** sdpconstval = NULL;
2402  int** indchanges = NULL;
2403  int* nremovedinds = NULL;
2404  SCIP_Real* lplhsafterfix;
2405  SCIP_Real* lprhsafterfix;
2406  SCIP_Real solvertimelimit;
2407  SCIP_Bool fixingfound;
2408  clock_t starttime;
2409  clock_t currenttime;
2410  int* rowsnactivevars;
2411  int* blockindchanges;
2412  int sdpconstnnonz;
2413  int nactivelpcons;
2414  int nremovedblocks = 0;
2415  int block;
2416  int naddediterations;
2417  int naddedsdpcalls;
2418 
2419  assert( sdpi != NULL );
2420 
2421  starttime = clock();
2422 
2423  SCIPdebugMessage("Forwarding SDP %d to solver!\n", sdpi->sdpid);
2424 
2425  sdpi->penalty = FALSE;
2426  sdpi->bestbound = -SCIPsdpiSolverInfinity(sdpi->sdpisolver);
2427  sdpi->solved = FALSE;
2428  sdpi->nsdpcalls = 0;
2429  sdpi->niterations = 0;
2430 
2431  /* allocate memory for computing the constant matrix after fixings and finding empty rows and columns, this is as much as might possibly be
2432  * needed, this will be shrinked again before solving */
2433  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &sdpconstnblocknonz, sdpi->nsdpblocks) );
2434  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &sdpconstrow, sdpi->nsdpblocks) );
2435  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &sdpconstcol, sdpi->nsdpblocks) );
2436  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &sdpconstval, sdpi->nsdpblocks) );
2437  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &indchanges, sdpi->nsdpblocks) );
2438  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &nremovedinds, sdpi->nsdpblocks) );
2439  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &blockindchanges, sdpi->nsdpblocks) );
2440  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &lplhsafterfix, sdpi->nlpcons) );
2441  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &lprhsafterfix, sdpi->nlpcons) );
2442  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &rowsnactivevars, sdpi->nlpcons) );
2443 
2444  for (block = 0; block < sdpi->nsdpblocks; block++)
2445  {
2446  sdpconstrow[block] = NULL;
2447  sdpconstcol[block] = NULL;
2448  sdpconstval[block] = NULL;
2449  indchanges[block] = NULL;
2450  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &(indchanges[block]), sdpi->sdpblocksizes[block]) );
2451  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &(sdpconstrow[block]), sdpi->sdpnnonz + sdpi->sdpconstnnonz) ); /*lint !e776*/
2452  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &(sdpconstcol[block]), sdpi->sdpnnonz + sdpi->sdpconstnnonz) ); /*lint !e776*/
2453  BMS_CALL( BMSallocBlockMemoryArray(sdpi->blkmem, &(sdpconstval[block]), sdpi->sdpnnonz + sdpi->sdpconstnnonz) ); /*lint !e776*/
2454  }
2455 
2456  /* compute the lplphss and lprhss, detect empty rows and check for additional variable fixings caused by boundchanges from
2457  * lp rows with a single active variable */
2458  do
2459  {
2460  fixingfound = FALSE;
2461  SCIP_CALL( computeLpLhsRhsAfterFixings(sdpi, &nactivelpcons, lplhsafterfix, lprhsafterfix, rowsnactivevars, &fixingfound) );
2462  }
2463  while ( fixingfound );
2464 
2465  /* initialize sdpconstnblocknonz */
2466  for (block = 0; block < sdpi->nsdpblocks; block++)
2467  sdpconstnblocknonz[block] = sdpi->sdpnnonz + sdpi->sdpconstnnonz;
2468 
2469  SCIP_CALL( compConstMatAfterFixings(sdpi, &sdpconstnnonz, sdpconstnblocknonz, sdpconstrow, sdpconstcol, sdpconstval) );
2470 
2471  /* shrink the constant arrays after the number of fixed nonzeros is known */
2472  for (block = 0; block < sdpi->nsdpblocks; block++)
2473  {
2474  assert ( sdpconstnblocknonz[block] <= sdpi->sdpnnonz + sdpi->sdpconstnnonz ); /* otherwise the memory wasn't sufficient,
2475  * but we allocated more than enough */
2476  BMS_CALL( BMSreallocBlockMemoryArray(sdpi->blkmem, &(sdpconstrow[block]), sdpi->sdpnnonz + sdpi->sdpconstnnonz, sdpconstnblocknonz[block]) ); /*lint !e776*/
2477  BMS_CALL( BMSreallocBlockMemoryArray(sdpi->blkmem, &(sdpconstcol[block]), sdpi->sdpnnonz + sdpi->sdpconstnnonz, sdpconstnblocknonz[block]) ); /*lint !e776*/
2478  BMS_CALL( BMSreallocBlockMemoryArray(sdpi->blkmem, &(sdpconstval[block]), sdpi->sdpnnonz + sdpi->sdpconstnnonz, sdpconstnblocknonz[block]) ); /*lint !e776*/
2479  }
2480 
2481  SCIP_CALL( findEmptyRowColsSDP(sdpi, sdpconstnblocknonz, sdpconstrow, sdpconstcol, sdpconstval, indchanges, nremovedinds, blockindchanges, &nremovedblocks) );
2482 
2483  /* check if all variables are fixed, if this is the case, check if the remaining solution if feasible (we only need to check the SDP-constraint,
2484  * the linear constraints were already checked in computeLpLhsRhsAfterFixings) */
2485  SCIP_CALL( checkAllFixed(sdpi) );
2486  if ( sdpi->allfixed && ! sdpi->infeasible )
2487  {
2488  SCIP_CALL( checkFixedFeasibilitySdp(sdpi, sdpconstnblocknonz, sdpconstrow, sdpconstcol, sdpconstval, indchanges, nremovedinds, blockindchanges) );
2489  }
2490 
2491  if ( sdpi->infeasible )
2492  {
2493  SCIPdebugMessage("SDP %d not given to solver, as infeasibility was detected during presolving!\n", sdpi->sdpid++);
2494  SCIP_CALL( SCIPsdpiSolverIncreaseCounter(sdpi->sdpisolver) );
2495 
2496  sdpi->solved = TRUE;
2497  sdpi->dualslater = SCIP_SDPSLATER_NOINFO;
2498  sdpi->primalslater = SCIP_SDPSLATER_NOINFO;
2499  }
2500  else if ( sdpi->allfixed )
2501  {
2502  SCIPdebugMessage("SDP %d not given to solver, as all variables were fixed during presolving (the solution was feasible)!\n", sdpi->sdpid++);
2503  SCIP_CALL( SCIPsdpiSolverIncreaseCounter(sdpi->sdpisolver) );
2504 
2505  sdpi->solved = TRUE;
2506  sdpi->dualslater = SCIP_SDPSLATER_NOINFO;
2507  sdpi->primalslater = SCIP_SDPSLATER_NOINFO;
2508  }
2509  else
2510  {
2511  if ( sdpi->slatercheck )
2512  {
2513  SCIP_CALL( checkSlaterCondition(sdpi, timelimit, starttime, sdpconstnblocknonz, sdpconstrow, sdpconstcol, sdpconstval, indchanges,
2514  nremovedinds, lplhsafterfix, lprhsafterfix, rowsnactivevars, blockindchanges, sdpconstnnonz, nactivelpcons, nremovedblocks, FALSE) );
2515  }
2516 
2517  /* compute the timit limit to set for the solver */
2518  solvertimelimit = timelimit;
2519  if ( ! SCIPsdpiIsInfinity(sdpi, solvertimelimit) )
2520  {
2521  currenttime = clock();
2522  solvertimelimit -= (SCIP_Real)(currenttime - starttime) / (SCIP_Real) CLOCKS_PER_SEC;/*lint !e620*/
2523  }
2524 
2525  /* try to solve the problem */
2526  SCIP_CALL( SCIPsdpiSolverLoadAndSolve(sdpi->sdpisolver, sdpi->nvars, sdpi->obj, sdpi->lb, sdpi->ub,
2527  sdpi->nsdpblocks, sdpi->sdpblocksizes, sdpi->sdpnblockvars, sdpconstnnonz,
2528  sdpconstnblocknonz, sdpconstrow, sdpconstcol, sdpconstval,
2529  sdpi->sdpnnonz, sdpi->sdpnblockvarnonz, sdpi->sdpvar, sdpi->sdprow, sdpi->sdpcol,
2530  sdpi->sdpval, indchanges, nremovedinds, blockindchanges, nremovedblocks, nactivelpcons, sdpi->nlpcons, lplhsafterfix, lprhsafterfix,
2531  rowsnactivevars, sdpi->lpnnonz, sdpi->lprow, sdpi->lpcol, sdpi->lpval, start, startsettings, solvertimelimit) );
2532 
2533  sdpi->solved = TRUE;
2534 
2535  /* add iterations and sdpcalls */
2536  naddediterations = 0;
2537  SCIP_CALL( SCIPsdpiSolverGetIterations(sdpi->sdpisolver, &naddediterations) );
2538  sdpi->niterations += naddediterations;
2539  naddedsdpcalls = 0;
2540  SCIP_CALL( SCIPsdpiSolverGetSdpCalls(sdpi->sdpisolver, &naddedsdpcalls) );
2541  sdpi->nsdpcalls += naddedsdpcalls;
2542 
2543  /* if the solver didn't produce a satisfactory result, we have to try with a penalty formulation */
2544  if ( ! SCIPsdpiSolverIsAcceptable(sdpi->sdpisolver) && ! SCIPsdpiSolverIsTimelimExc(sdpi->sdpisolver) )
2545  {
2546  SCIP_Real penaltyparam;
2547  SCIP_Real penaltyparamfact;
2548  SCIP_Real epsilon;
2549  SCIP_Real epsilonfact;
2550  SCIP_Bool feasorig;
2551  SCIP_Bool penaltybound;
2552  SCIP_Real objbound;
2553  SCIP_Real objval;
2554 
2555  feasorig = FALSE;
2556  penaltybound = TRUE;
2557 
2558  /* first check feasibility using the penalty approach */
2559 
2560  /* compute the timit limit to set for the solver */
2561  solvertimelimit = timelimit;
2562  if ( ! SCIPsdpiIsInfinity(sdpi, solvertimelimit) )
2563  {
2564  currenttime = clock();
2565  solvertimelimit -= (SCIP_Real)(currenttime - starttime) / (SCIP_Real) CLOCKS_PER_SEC;/*lint !e620*/
2566  }
2567 
2568  /* we solve the problem with a slack variable times identity added to the constraints and trying to minimize this slack variable r, if
2569  * the optimal objective is bigger than feastol, then we know that the problem is infeasible */
2570  SCIP_CALL( SCIPsdpiSolverLoadAndSolveWithPenalty(sdpi->sdpisolver, 1.0, FALSE, FALSE, sdpi->nvars, sdpi->obj, sdpi->lb, sdpi->ub,
2571  sdpi->nsdpblocks, sdpi->sdpblocksizes, sdpi->sdpnblockvars, sdpconstnnonz,
2572  sdpconstnblocknonz, sdpconstrow, sdpconstcol, sdpconstval,
2573  sdpi->sdpnnonz, sdpi->sdpnblockvarnonz, sdpi->sdpvar, sdpi->sdprow, sdpi->sdpcol,
2574  sdpi->sdpval, indchanges, nremovedinds, blockindchanges, nremovedblocks, nactivelpcons, sdpi->nlpcons, lplhsafterfix, lprhsafterfix,
2575  rowsnactivevars, sdpi->lpnnonz, sdpi->lprow, sdpi->lpcol, sdpi->lpval, start, SCIP_SDPSOLVERSETTING_UNSOLVED, solvertimelimit,
2576  &feasorig, &penaltybound) );
2577 
2578  /* add iterations and sdpcalls */
2579  naddediterations = 0;
2580  SCIP_CALL( SCIPsdpiSolverGetIterations(sdpi->sdpisolver, &naddediterations) );
2581  sdpi->niterations += naddediterations;
2582  naddedsdpcalls = 0;
2583  SCIP_CALL( SCIPsdpiSolverGetSdpCalls(sdpi->sdpisolver, &naddedsdpcalls) );
2584  sdpi->nsdpcalls += naddedsdpcalls;
2585 
2586  /* get objective value */
2587  if ( SCIPsdpiSolverWasSolved(sdpi->sdpisolver) )
2588  {
2589  SCIP_CALL( SCIPsdpiSolverGetObjval(sdpi->sdpisolver, &objval) );
2590  }
2591  else
2592  objval = -SCIPsdpiInfinity(sdpi);
2593 
2594  if ( (SCIPsdpiSolverIsOptimal(sdpi->sdpisolver) && objval > sdpi->epsilon) || SCIPsdpiSolverIsDualInfeasible(sdpi->sdpisolver))
2595  {
2596  SCIPdebugMessage("SDP %d found infeasible using penalty formulation, maximum of smallest eigenvalue is %f.\n", sdpi->sdpid, -1.0 * objval);
2597  sdpi->penalty = TRUE;
2598  sdpi->infeasible = TRUE;
2599  }
2600  else
2601  {
2602  feasorig = FALSE;
2603  penaltybound = TRUE;
2604 
2605  penaltyparam = sdpi->penaltyparam;
2606 
2607  /* we compute the factor to increase with as n-th root of the total increase until the maximum, where n is the number of iterations */
2608  penaltyparamfact = pow((sdpi->maxpenaltyparam / sdpi->penaltyparam), 1.0/NINCREASESGAMMA);
2609  epsilon = sdpi->epsilon;
2610  epsilonfact = pow((MIN_EPSILON / sdpi->epsilon), 1.0/NINCREASESGAMMA);
2611 
2612  /* increase penalty-param and decrease feasibility tolerance until we find a feasible solution or reach the final bound for either one of them */
2613  while ( ( ! SCIPsdpiSolverIsAcceptable(sdpi->sdpisolver) || ! feasorig ) &&
2614  ( penaltyparam < sdpi->maxpenaltyparam + sdpi->epsilon ) && ( epsilon > 0.99 * MIN_EPSILON ) && ( ! SCIPsdpiSolverIsTimelimExc(sdpi->sdpisolver) ))
2615  {
2616  SCIPdebugMessage("Solver did not produce an acceptable result, trying SDP %d again with penaltyparameter %f\n", sdpi->sdpid, penaltyparam);
2617 
2618  /* compute the timit limit to set for the solver */
2619  solvertimelimit = timelimit;
2620  if ( ! SCIPsdpiIsInfinity(sdpi, solvertimelimit) )
2621  {
2622  currenttime = clock();
2623  solvertimelimit -= (SCIP_Real)(currenttime - starttime) / (SCIP_Real) CLOCKS_PER_SEC;/*lint !e620*/
2624  }
2625 
2626  SCIP_CALL( SCIPsdpiSolverLoadAndSolveWithPenalty(sdpi->sdpisolver, penaltyparam, TRUE, TRUE, sdpi->nvars, sdpi->obj,
2627  sdpi->lb, sdpi->ub, sdpi->nsdpblocks, sdpi->sdpblocksizes, sdpi->sdpnblockvars, sdpconstnnonz,
2628  sdpconstnblocknonz, sdpconstrow, sdpconstcol, sdpconstval,
2629  sdpi->sdpnnonz, sdpi->sdpnblockvarnonz, sdpi->sdpvar, sdpi->sdprow, sdpi->sdpcol,
2630  sdpi->sdpval, indchanges, nremovedinds, blockindchanges, nremovedblocks, nactivelpcons, sdpi->nlpcons, lplhsafterfix, lprhsafterfix,
2631  rowsnactivevars, sdpi->lpnnonz, sdpi->lprow, sdpi->lpcol, sdpi->lpval, start, startsettings, solvertimelimit, &feasorig, &penaltybound) );
2632 
2633  /* add iterations and sdpcalls */
2634  naddediterations = 0;
2635  SCIP_CALL( SCIPsdpiSolverGetIterations(sdpi->sdpisolver, &naddediterations) );
2636  sdpi->niterations += naddediterations;
2637  naddedsdpcalls = 0;
2638  SCIP_CALL( SCIPsdpiSolverGetSdpCalls(sdpi->sdpisolver, &naddedsdpcalls) );
2639  sdpi->nsdpcalls += naddedsdpcalls;
2640 
2641  /* If the solver did not converge, we increase the penalty parameter */
2642  if ( ! SCIPsdpiSolverIsAcceptable(sdpi->sdpisolver) )
2643  {
2644  penaltyparam *= penaltyparamfact;
2645  SCIPdebugMessage("Solver did not converge even with penalty formulation, increasing penaltyparameter.\n");
2646  continue;
2647  }
2648 
2649  /* if we succeeded to solve the problem, update the bound */
2650  SCIP_CALL( SCIPsdpiSolverGetObjval(sdpi->sdpisolver, &objbound) );
2651  if ( objbound > sdpi->bestbound + sdpi->epsilon )
2652  sdpi->bestbound = objbound;
2653 
2654  /* If we don't get a feasible solution to our original problem we have to update either Gamma (if the penalty bound was active
2655  * in the primal problem) or epsilon (otherwise) */
2656  if ( ! feasorig )
2657  {
2658  if ( penaltybound )
2659  {
2660  penaltyparam *= penaltyparamfact;
2661  SCIPdebugMessage("Penalty formulation produced a result which is infeasible for the original problem, increasing penaltyparameter\n");
2662  }
2663  else
2664  {
2665  epsilon *= epsilonfact;
2666  SCIP_CALL_PARAM( SCIPsdpiSolverSetRealpar(sdpi->sdpisolver, SCIP_SDPPAR_EPSILON, epsilon) );
2667  SCIPdebugMessage("Penalty formulation produced a result which is infeasible for the original problem, even though primal penalty "
2668  "bound was not reached, decreasing epsilon value for duality gap in SDP-solver\n");
2669  }
2670  }
2671  }
2672 
2673  /* reset the feasibility tolerance in the SDP-solver */
2674  if ( epsilon > sdpi->epsilon )
2675  {
2676  SCIP_CALL_PARAM( SCIPsdpiSolverSetRealpar(sdpi->sdpisolver, SCIP_SDPPAR_EPSILON, sdpi->epsilon) );
2677  }
2678 
2679  /* check if we were able to solve the problem in the end */
2680  if ( SCIPsdpiSolverIsAcceptable(sdpi->sdpisolver) && feasorig )
2681  {
2682  sdpi->penalty = TRUE;
2683  sdpi->solved = TRUE;
2684  }
2685 #if 0 /* we don't really know if it is infeasible or just ill-posed (no KKT-point) */
2686  else if ( SCIPsdpiSolverIsAcceptable(sdpi->sdpisolver) && ! feasorig )
2687  {
2688  SCIPdebugMessage("Problem was found to be infeasible using a penalty formulation \n");
2689  sdpi->infeasible = TRUE;
2690  sdpi->penalty = TRUE;
2691  sdpi->solved = TRUE;
2692  }
2693 #endif
2694  else
2695  {
2696  SCIPdebugMessage("SDP-Solver could not solve the problem even after using a penalty formulation \n");
2697  sdpi->solved = FALSE;
2698  sdpi->penalty = TRUE;
2699  }
2700 
2701  /* if we still didn't succeed and enforceslatercheck was set, we finally test for the Slater condition to give a reason for failure */
2702  if ( sdpi->solved == FALSE && enforceslatercheck)
2703  {
2704  SCIP_CALL( checkSlaterCondition(sdpi, timelimit, starttime, sdpconstnblocknonz, sdpconstrow, sdpconstcol, sdpconstval, indchanges,
2705  nremovedinds, lplhsafterfix, lprhsafterfix, rowsnactivevars, blockindchanges, sdpconstnnonz, nactivelpcons, nremovedblocks, TRUE) );
2706  }
2707  else if ( sdpi->solved == FALSE )
2708 #if 0
2709  SCIPmessagePrintInfo(sdpi->messagehdlr, "Numerical trouble\n");
2710 #else
2711  SCIPdebugMessage("SDP-Interface was unable to solve SDP %d\n", sdpi->sdpid);
2712 #endif
2713  }
2714  }
2715  }
2716 
2717  /* empty the memory allocated here */
2718  for (block = 0; block < sdpi->nsdpblocks; block++)
2719  {
2720  BMSfreeBlockMemoryArray(sdpi->blkmem, &(sdpconstval[block]), sdpconstnblocknonz[block]);/*lint !e737*/
2721  BMSfreeBlockMemoryArray(sdpi->blkmem, &(sdpconstcol[block]), sdpconstnblocknonz[block]);/*lint !e737*/
2722  BMSfreeBlockMemoryArray(sdpi->blkmem, &(sdpconstrow[block]), sdpconstnblocknonz[block]);/*lint !e737*/
2723  BMSfreeBlockMemoryArray(sdpi->blkmem, &(indchanges[block]), sdpi->sdpblocksizes[block]);/*lint !e737*/
2724  }
2725  BMSfreeBlockMemoryArray(sdpi->blkmem, &rowsnactivevars, sdpi->nlpcons);/*lint !e737*/
2726  BMSfreeBlockMemoryArray(sdpi->blkmem, &lprhsafterfix, sdpi->nlpcons);/*lint !e737*/
2727  BMSfreeBlockMemoryArray(sdpi->blkmem, &lplhsafterfix, sdpi->nlpcons);/*lint !e737*/
2728  BMSfreeBlockMemoryArray(sdpi->blkmem, &blockindchanges, sdpi->nsdpblocks);/*lint !e737*/
2729  BMSfreeBlockMemoryArray(sdpi->blkmem, &nremovedinds, sdpi->nsdpblocks);/*lint !e737*/
2730  BMSfreeBlockMemoryArray(sdpi->blkmem, &indchanges, sdpi->nsdpblocks);/*lint !e737*/
2731  BMSfreeBlockMemoryArray(sdpi->blkmem, &sdpconstval, sdpi->nsdpblocks);/*lint !e737*/
2732  BMSfreeBlockMemoryArray(sdpi->blkmem, &sdpconstcol, sdpi->nsdpblocks);/*lint !e737*/
2733  BMSfreeBlockMemoryArray(sdpi->blkmem, &sdpconstrow, sdpi->nsdpblocks);/*lint !e737*/
2734  BMSfreeBlockMemoryArray(sdpi->blkmem, &sdpconstnblocknonz, sdpi->nsdpblocks);/*lint !e737*/
2735 
2736  sdpi->sdpid++;
2737 
2738  return SCIP_OKAY;
2739 }
2740 
2741 
2742 
2743 
2744 /*
2745  * Solution Information Methods
2746  */
2747 
2753  SCIP_SDPI* sdpi
2754  )
2755 {
2756  assert( sdpi != NULL );
2757 
2758  return sdpi->solved;
2759 }
2760 
2763  SCIP_SDPI* sdpi
2764  )
2765 {
2766  assert( sdpi != NULL );
2767 
2768  return ( ! sdpi->penalty );
2769 }
2770 
2775  SCIP_SDPI* sdpi
2776  )
2777 {
2778  assert( sdpi != NULL );
2779  CHECK_IF_SOLVED_BOOL(sdpi);
2780 
2781  if ( sdpi->infeasible || sdpi->allfixed )
2782  return TRUE;
2783 
2784  return SCIPsdpiSolverFeasibilityKnown(sdpi->sdpisolver);
2785 }
2786 
2789  SCIP_SDPI* sdpi,
2790  SCIP_Bool* primalfeasible,
2791  SCIP_Bool* dualfeasible
2792  )
2793 {
2794  assert( sdpi != NULL );
2795  CHECK_IF_SOLVED(sdpi);
2796 
2797  if ( sdpi->infeasible )
2798  {
2799  SCIPdebugMessage("Problem was found infeasible during preprocessing, primal feasibility not available\n");
2800  *dualfeasible = FALSE;
2801  return SCIP_OKAY;
2802  }
2803  else if ( sdpi->allfixed )
2804  {
2805  SCIPdebugMessage("All variables were fixed during preprocessing, dual problem is feasible, primal feasibility not available\n");
2806  *dualfeasible = TRUE;
2807  return SCIP_OKAY;
2808  }
2809 
2810  SCIP_CALL( SCIPsdpiSolverGetSolFeasibility(sdpi->sdpisolver, primalfeasible, dualfeasible) );
2811 
2812  return SCIP_OKAY;
2813 }
2814 
2818  SCIP_SDPI* sdpi
2819  )
2820 {
2821  assert( sdpi != NULL );
2822  CHECK_IF_SOLVED_BOOL(sdpi);
2823 
2824  if ( sdpi->infeasible )
2825  {
2826  SCIPdebugMessage("Problem was found infeasible during preprocessing, primal unboundedness not available\n");
2827  return FALSE;
2828  }
2829  else if ( sdpi->allfixed )
2830  {
2831  SCIPdebugMessage("All variables were fixed during preprocessing, primal unboundedness not available\n");
2832  return FALSE;
2833  }
2834 
2835  return SCIPsdpiSolverIsPrimalUnbounded(sdpi->sdpisolver);
2836 }
2837 
2841  SCIP_SDPI* sdpi
2842  )
2843 {
2844  assert( sdpi != NULL );
2845  CHECK_IF_SOLVED_BOOL(sdpi);
2846 
2847  if ( sdpi->infeasible )
2848  {
2849  SCIPdebugMessage("Problem was found infeasible during preprocessing, primal feasibility not available\n");
2850  return FALSE;
2851  }
2852  else if ( sdpi->allfixed )
2853  {
2854  SCIPdebugMessage("All variables were fixed during preprocessing, primal feasibility not available\n");
2855  return FALSE;
2856  }
2857 
2858  return SCIPsdpiSolverIsPrimalInfeasible(sdpi->sdpisolver);
2859 }
2860 
2864  SCIP_SDPI* sdpi
2865  )
2866 {
2867  assert(sdpi != NULL );
2868  CHECK_IF_SOLVED_BOOL(sdpi);
2869 
2870  if ( sdpi->infeasible )
2871  {
2872  SCIPdebugMessage("Problem was found infeasible during preprocessing, primal feasibility not available\n");
2873  return FALSE;
2874  }
2875  else if ( sdpi->allfixed )
2876  {
2877  SCIPdebugMessage("All variables fixed during preprocessing, primal feasibility not available\n");
2878  return FALSE;
2879  }
2880 
2881  return SCIPsdpiSolverIsPrimalFeasible(sdpi->sdpisolver);
2882 }
2883 
2887  SCIP_SDPI* sdpi
2888  )
2889 {
2890  assert( sdpi != NULL );
2891  CHECK_IF_SOLVED_BOOL(sdpi);
2892 
2893  if ( sdpi->infeasible )
2894  {
2895  SCIPdebugMessage("Problem was found infeasible during preprocessing, therefore is not unbounded\n");
2896  return FALSE;
2897  }
2898  else if ( sdpi->allfixed )
2899  {
2900  SCIPdebugMessage("All variables were fixed during preprocessing, therefore the problem is not unbounded\n");
2901  return FALSE;
2902  }
2903 
2904  return SCIPsdpiSolverIsDualUnbounded(sdpi->sdpisolver);
2905 }
2906 
2910  SCIP_SDPI* sdpi
2911  )
2912 {
2913  assert( sdpi != NULL );
2914  CHECK_IF_SOLVED_BOOL(sdpi);
2915 
2916  if ( sdpi->infeasible )
2917  {
2918  SCIPdebugMessage("Problem was found infeasible during preprocessing\n");
2919  return TRUE;
2920  }
2921  else if ( sdpi->allfixed )
2922  {
2923  SCIPdebugMessage("All variables were fixed during preprocessing, solution is feasible\n");
2924  return FALSE;
2925  }
2926 
2927  return SCIPsdpiSolverIsDualInfeasible(sdpi->sdpisolver);
2928 }
2929 
2933  SCIP_SDPI* sdpi
2934  )
2935 {
2936  assert( sdpi != NULL );
2937  CHECK_IF_SOLVED_BOOL(sdpi);
2938 
2939  if ( sdpi->infeasible )
2940  {
2941  SCIPdebugMessage("Problem was found infeasible during preprocessing\n");
2942  return FALSE;
2943  }
2944  else if ( sdpi->allfixed )
2945  {
2946  SCIPdebugMessage("All variables fixed during preprocessing, solution is feasible\n");
2947  return TRUE;
2948  }
2949 
2950  return SCIPsdpiSolverIsDualFeasible(sdpi->sdpisolver);
2951 }
2952 
2955  SCIP_SDPI* sdpi
2956  )
2957 {
2958  assert( sdpi != NULL );
2959  CHECK_IF_SOLVED_BOOL(sdpi);
2960 
2961  if ( sdpi->infeasible )
2962  {
2963  SCIPdebugMessage("Problem was found infeasible during preprocessing, this counts as converged.\n");
2964  return TRUE;
2965  }
2966  else if ( sdpi->allfixed )
2967  {
2968  SCIPdebugMessage("All variables were fixed during preprocessing, this counts as converged.\n");
2969  return TRUE;
2970  }
2971 
2972  return SCIPsdpiSolverIsConverged(sdpi->sdpisolver);
2973 }
2974 
2977  SCIP_SDPI* sdpi
2978  )
2979 {
2980  assert( sdpi != NULL );
2981  CHECK_IF_SOLVED_BOOL(sdpi);
2982 
2983  if ( sdpi->infeasible )
2984  {
2985  SCIPdebugMessage("Problem was found infeasible during preprocessing, no objective limit available.\n");
2986  return FALSE;
2987  }
2988  else if ( sdpi->allfixed )
2989  {
2990  SCIPdebugMessage("All variables were fixed during preprocessing, no objective limit available.\n");
2991  return FALSE;
2992  }
2993 
2994  return SCIPsdpiSolverIsObjlimExc(sdpi->sdpisolver);
2995 }
2996 
2999  SCIP_SDPI* sdpi
3000  )
3001 {
3002  assert( sdpi != NULL );
3003  CHECK_IF_SOLVED_BOOL(sdpi);
3004 
3005  if ( sdpi->infeasible )
3006  {
3007  SCIPdebugMessage("Problem was found infeasible during preprocessing, no iteration limit available.\n");
3008  return FALSE;
3009  }
3010  else if ( sdpi->allfixed )
3011  {
3012  SCIPdebugMessage("All variables were fixed during preprocessing, no iteration limit available.\n");
3013  return FALSE;
3014  }
3015 
3016  return SCIPsdpiSolverIsIterlimExc(sdpi->sdpisolver);
3017 }
3018 
3021  SCIP_SDPI* sdpi
3022  )
3023 {
3024  assert( sdpi != NULL );
3025 
3026  if ( sdpi->infeasible )
3027  {
3028  SCIPdebugMessage("Problem was found infeasible during preprocessing, no time limit available.\n");
3029  return FALSE;
3030  }
3031  else if ( sdpi->allfixed )
3032  {
3033  SCIPdebugMessage("All variables were fixed during preprocessing, no time limit available.\n");
3034  return FALSE;
3035  }
3036  else if ( ! sdpi->solved )
3037  {
3038  SCIPdebugMessage("Problem was not solved, time limit not exceeded.\n");
3039  return FALSE;
3040  }
3041 
3042  return SCIPsdpiSolverIsTimelimExc(sdpi->sdpisolver);
3043 }
3044 
3056  SCIP_SDPI* sdpi
3057  )
3058 {
3059  assert( sdpi != NULL );
3060 
3061  if ( ! sdpi->solved )
3062  {
3063  SCIPdebugMessage("Problem wasn't solved yet.\n");
3064  return -1;
3065  }
3066  else if ( sdpi->infeasible )
3067  {
3068  SCIPdebugMessage("Problem was found infeasible during preprocessing, no internal status available.\n");
3069  return 0;
3070  }
3071  else if ( sdpi->allfixed )
3072  {
3073  SCIPdebugMessage("All variables were fixed during preprocessing, no internal status available.\n");
3074  return 0;
3075  }
3076 
3077  return SCIPsdpiSolverGetInternalStatus(sdpi->sdpisolver);
3078 }
3079 
3082  SCIP_SDPI* sdpi
3083  )
3084 {
3085  assert( sdpi != NULL );
3086  CHECK_IF_SOLVED_BOOL(sdpi);
3087 
3088  if ( sdpi->infeasible )
3089  {
3090  SCIPdebugMessage("Problem was found infeasible during preprocessing, therefore there is no optimal solution.\n");
3091  return FALSE;
3092  }
3093  else if ( sdpi->allfixed )
3094  {
3095  SCIPdebugMessage("All variables were fixed during preprocessing, therefore there is no optimal solution.\n");
3096  return FALSE;
3097  }
3098 
3099  return SCIPsdpiSolverIsOptimal(sdpi->sdpisolver);
3100 }
3101 
3105  SCIP_SDPI* sdpi
3106  )
3107 {
3108  assert( sdpi != NULL );
3109 
3110  if ( sdpi->infeasible )
3111  {
3112  SCIPdebugMessage("Problem was found infeasible during preprocessing, this is acceptable in a B&B context.\n");
3113  return TRUE;
3114  }
3115  else if ( sdpi->allfixed )
3116  {
3117  SCIPdebugMessage("All variables fixed during preprocessing, this is acceptable in a B&B context.\n");
3118  return TRUE;
3119  }
3120  else if ( ! sdpi->solved )
3121  {
3122  SCIPdebugMessage("Problem not solved succesfully, this is not acceptable in a B&B context.\n");
3123  return FALSE;
3124  }
3125 
3126  return SCIPsdpiSolverIsAcceptable(sdpi->sdpisolver);
3127 }
3128 
3130 SCIP_RETCODE SCIPsdpiGetObjval(
3131  SCIP_SDPI* sdpi,
3132  SCIP_Real* objval
3133  )
3134 {
3135  assert( sdpi != NULL );
3136  assert( objval != NULL );
3137  CHECK_IF_SOLVED(sdpi);
3138 
3139  if ( sdpi->infeasible )
3140  {
3141  SCIPdebugMessage("Problem was found infeasible during preprocessing, no objective value available.\n");
3142  return SCIP_OKAY;
3143  }
3144 
3145  if ( sdpi->allfixed )
3146  {
3147  int v;
3148 
3149  /* As all variables were fixed during preprocessing, we have to compute it ourselves here */
3150  *objval = 0;
3151 
3152  for (v = 0; v < sdpi->nvars; v++)
3153  *objval += sdpi->lb[v] * sdpi->obj[v];
3154 
3155  return SCIP_OKAY;
3156  }
3157 
3158  SCIP_CALL( SCIPsdpiSolverGetObjval(sdpi->sdpisolver, objval) );
3159 
3160  return SCIP_OKAY;
3161 }
3162 
3166  SCIP_SDPI* sdpi,
3167  SCIP_Real* objlb
3168  )
3169 {
3170  assert( sdpi != NULL );
3171  assert( objlb != NULL );
3172 
3173  /* if we could successfully solve the problem, the best bound is the optimal objective */
3174  if ( sdpi->solved )
3175  {
3176  if ( sdpi->infeasible )
3177  {
3178  SCIPdebugMessage("Problem was found infeasible during preprocessing, no objective value available.\n");
3179  return SCIP_OKAY;
3180  }
3181 
3182  if ( sdpi->allfixed )
3183  {
3184  int v;
3185 
3186  /* As all variables were fixed during preprocessing, we have to compute it ourselves here */
3187  *objlb = 0;
3188 
3189  for (v = 0; v < sdpi->nvars; v++)
3190  *objlb += sdpi->lb[v] * sdpi->obj[v];
3191 
3192  return SCIP_OKAY;
3193  }
3194 
3195  SCIP_CALL( SCIPsdpiSolverGetObjval(sdpi->sdpisolver, objlb) );
3196  return SCIP_OKAY;
3197  }
3198 
3199  /* if we could not solve it, but tried the penalty formulation, we take the best bound computed by the penalty approach */
3200  if ( sdpi->penalty )
3201  {
3202  *objlb = sdpi->bestbound;
3203  return SCIP_OKAY;
3204  }
3205 
3206  /* if we could not solve it and did not use the penalty formulation (e.g. because the time limit was reached), we have no information */
3207 
3208  *objlb = -SCIPsdpiInfinity(sdpi);
3209  return SCIP_OKAY;
3210 }
3211 
3214 SCIP_RETCODE SCIPsdpiGetSol(
3215  SCIP_SDPI* sdpi,
3216  SCIP_Real* objval,
3217  SCIP_Real* dualsol,
3218  int* dualsollength
3220  )
3221 {
3222  assert( sdpi != NULL );
3223  assert( dualsollength != NULL );
3224  assert( *dualsollength == 0 || dualsol != NULL );
3225  CHECK_IF_SOLVED(sdpi);
3226 
3227  if ( sdpi->infeasible )
3228  {
3229  SCIPdebugMessage("Problem was found infeasible during preprocessing, no solution available.\n");
3230  return SCIP_OKAY;
3231  }
3232  else if ( sdpi->allfixed )
3233  {
3234  if ( objval != NULL )
3235  {
3236  SCIP_CALL( SCIPsdpiGetObjval(sdpi, objval) );
3237  }
3238  if ( *dualsollength > 0 )
3239  {
3240  int v;
3241 
3242  assert( dualsol != NULL );
3243  if ( *dualsollength < sdpi->nvars )
3244  {
3245  SCIPdebugMessage("The given array in SCIPsdpiGetSol only had length %d, but %d was needed", *dualsollength, sdpi->nvars);
3246  *dualsollength = sdpi->nvars;
3247 
3248  return SCIP_OKAY;
3249  }
3250 
3251  /* we give the fixed values as the solution */
3252  for (v = 0; v < sdpi->nvars; v++)
3253  dualsol[v] = sdpi->lb[v];
3254 
3255  return SCIP_OKAY;
3256  }
3257  }
3258 
3259  SCIP_CALL( SCIPsdpiSolverGetSol(sdpi->sdpisolver, objval, dualsol, dualsollength) );
3260 
3261  return SCIP_OKAY;
3262 }
3263 
3269  SCIP_SDPI* sdpi,
3270  SCIP_Real* lbvars,
3271  SCIP_Real* ubvars,
3272  int* arraylength
3274  )
3275 {
3276  assert( sdpi != NULL );
3277  assert( lbvars != NULL );
3278  assert( ubvars != NULL );
3279  assert( arraylength != NULL );
3280  assert( *arraylength >= 0 );
3281  CHECK_IF_SOLVED(sdpi);
3282 
3283  if ( sdpi->infeasible )
3284  {
3285  SCIPdebugMessage("Problem was found infeasible during preprocessing, no primal variables available.\n");
3286  return SCIP_OKAY;
3287  }
3288  else if ( sdpi->allfixed )
3289  {
3290  SCIPdebugMessage("All variables fixed during preprocessing, no primal variables available.\n");
3291  return SCIP_OKAY;
3292  }
3293 
3294  SCIP_CALL( SCIPsdpiSolverGetPrimalBoundVars(sdpi->sdpisolver, lbvars, ubvars, arraylength) );
3295 
3296  return SCIP_OKAY;
3297 }
3298 
3301  SCIP_SDPI* sdpi,
3302  int* iterations
3303  )
3304 {
3305  assert( sdpi != NULL );
3306  assert( iterations != NULL );
3307 
3308  *iterations = sdpi->niterations;
3309 
3310  return SCIP_OKAY;
3311 }
3312 
3314 SCIP_RETCODE SCIPsdpiGetSdpCalls(
3315  SCIP_SDPI* sdpi,
3316  int* calls
3317  )
3318 {
3319  assert( sdpi != NULL );
3320  assert( calls != NULL );
3321 
3322  *calls = sdpi->nsdpcalls;
3323 
3324  return SCIP_OKAY;
3325 }
3326 
3329  SCIP_SDPI* sdpi,
3330  SCIP_SDPSOLVERSETTING* usedsetting
3331  )
3332 {
3333  assert( sdpi != NULL );
3334  assert( usedsetting != NULL );
3335 
3336  if ( ! sdpi->solved )
3337  {
3338  SCIPdebugMessage("Problem was not solved successfully.\n");
3339  *usedsetting = SCIP_SDPSOLVERSETTING_UNSOLVED;
3340  return SCIP_OKAY;
3341  }
3342  else if ( sdpi->infeasible && ! sdpi->penalty ) /* if we solved the penalty formulation, we may also set infeasible if it is infeasible for the original problem */
3343  {
3344  SCIPdebugMessage("Problem was found infeasible during preprocessing, no settings used.\n");
3345  *usedsetting = SCIP_SDPSOLVERSETTING_UNSOLVED;
3346  return SCIP_OKAY;
3347  }
3348  else if ( sdpi->allfixed )
3349  {
3350  SCIPdebugMessage("All varialbes fixed during preprocessing, no settings used.\n");
3351  *usedsetting = SCIP_SDPSOLVERSETTING_UNSOLVED;
3352  return SCIP_OKAY;
3353  }
3354  else if ( sdpi->penalty )
3355  {
3356  *usedsetting = SCIP_SDPSOLVERSETTING_PENALTY;
3357  return SCIP_OKAY;
3358  }
3359 
3360  SCIP_CALL( SCIPsdpiSolverSettingsUsed(sdpi->sdpisolver, usedsetting) );
3361  return SCIP_OKAY;
3362 }
3363 
3366  SCIP_SDPI* sdpi,
3367  SCIP_SDPSLATERSETTING* slatersetting
3368  )
3369 {
3370  SCIP_SDPSOLVERSETTING usedsetting;
3371 
3372  assert( sdpi != NULL );
3373  assert( slatersetting != NULL );
3374 
3375  if ( ! sdpi->solved )
3376  {
3377  SCIPdebugMessage("Problem was not solved successfully");
3378  if ( sdpi->bestbound > -SCIPsdpiSolverInfinity(sdpi->sdpisolver) )
3379  {
3380  SCIPdebugMessage(", but we could at least compute a lower bound. \n");
3381  if ( sdpi->dualslater == SCIP_SDPSLATER_INF)
3382  *slatersetting = SCIP_SDPSLATERSETTING_BOUNDEDINFEASIBLE;
3383  else
3384  {
3385  switch( sdpi->primalslater )/*lint --e{788}*/
3386  {
3387  case SCIP_SDPSLATER_NOINFO:
3388  if ( sdpi->dualslater == SCIP_SDPSLATER_NOT )
3389  *slatersetting = SCIP_SDPSLATERSETTING_BOUNDEDNOSLATER;
3390  else
3391  *slatersetting = SCIP_SDPSLATERSETTING_NOINFO;
3392  break;
3393  case SCIP_SDPSLATER_NOT:
3394  *slatersetting = SCIP_SDPSLATERSETTING_BOUNDEDNOSLATER;
3395  break;
3396  case SCIP_SDPSLATER_HOLDS:
3397  switch( sdpi->dualslater )/*lint --e{788}*/
3398  {
3399  case SCIP_SDPSLATER_NOINFO:
3400  *slatersetting = SCIP_SDPSLATERSETTING_NOINFO;
3401  break;
3402  case SCIP_SDPSLATER_NOT:
3403  *slatersetting = SCIP_SDPSLATERSETTING_BOUNDEDNOSLATER;
3404  break;
3405  case SCIP_SDPSLATER_HOLDS:
3406  *slatersetting = SCIP_SDPSLATERSETTING_BOUNDEDWSLATER;
3407  break;
3408  default:
3409  *slatersetting = SCIP_SDPSLATERSETTING_NOINFO;
3410  break;
3411  }
3412  break;
3413  default:
3414  *slatersetting = SCIP_SDPSLATERSETTING_NOINFO;
3415  break;
3416  }
3417  }
3418  }
3419  else
3420  {
3421  SCIPdebugMessage(".\n");
3422  if ( sdpi->dualslater == SCIP_SDPSLATER_INF)
3424  else
3425  {
3426  switch( sdpi->primalslater )/*lint --e{788}*/
3427  {
3428  case SCIP_SDPSLATER_NOINFO:
3429  if ( sdpi->dualslater == SCIP_SDPSLATER_NOT )
3430  *slatersetting = SCIP_SDPSLATERSETTING_UNSOLVEDNOSLATER;
3431  else
3432  *slatersetting = SCIP_SDPSLATERSETTING_NOINFO;
3433  break;
3434  case SCIP_SDPSLATER_NOT:
3435  *slatersetting = SCIP_SDPSLATERSETTING_UNSOLVEDNOSLATER;
3436  break;
3437  case SCIP_SDPSLATER_HOLDS:
3438  switch( sdpi->dualslater )/*lint --e{788}*/
3439  {
3440  case SCIP_SDPSLATER_NOINFO:
3441  *slatersetting = SCIP_SDPSLATERSETTING_NOINFO;
3442  break;
3443  case SCIP_SDPSLATER_NOT:
3444  *slatersetting = SCIP_SDPSLATERSETTING_UNSOLVEDNOSLATER;
3445  break;
3446  case SCIP_SDPSLATER_HOLDS:
3447  *slatersetting = SCIP_SDPSLATERSETTING_UNSOLVEDWSLATER;
3448  break;
3449  default:
3450  *slatersetting = SCIP_SDPSLATERSETTING_NOINFO;
3451  break;
3452  }
3453  break;
3454  default:
3455  *slatersetting = SCIP_SDPSLATERSETTING_NOINFO;
3456  break;
3457  }
3458  }
3459  }
3460  return SCIP_OKAY;
3461  }
3462  else if ( sdpi->infeasible && ( ! sdpi->penalty ) ) /* if we solved the penalty formulation, we may also set infeasible if it is infeasible for the original problem */
3463  {
3464  SCIPdebugMessage("Problem was found infeasible during preprocessing, no settings used.\n");
3465  *slatersetting = SCIP_SDPSLATERSETTING_NOINFO;
3466  return SCIP_OKAY;
3467  }
3468  else if ( sdpi->allfixed )
3469  {
3470  SCIPdebugMessage("All varialbes fixed during preprocessing, no settings used.\n");
3471  *slatersetting = SCIP_SDPSLATERSETTING_NOINFO;
3472  return SCIP_OKAY;
3473  }
3474  else if ( sdpi->penalty )
3475  {
3476  switch( sdpi->primalslater )/*lint --e{788}*/
3477  {
3478  case SCIP_SDPSLATER_NOINFO:
3479  if ( sdpi->dualslater == SCIP_SDPSLATER_NOT )
3480  *slatersetting = SCIP_SDPSLATERSETTING_PENALTYNOSLATER;
3481  else if ( sdpi->dualslater == SCIP_SDPSLATER_INF )
3482  *slatersetting = SCIP_SDPSLATERSETTING_PENALTYINFEASIBLE;
3483  else
3484  *slatersetting = SCIP_SDPSLATERSETTING_NOINFO;
3485  break;
3486  case SCIP_SDPSLATER_NOT:
3487  if ( sdpi->dualslater == SCIP_SDPSLATER_INF )
3488  *slatersetting = SCIP_SDPSLATERSETTING_PENALTYINFEASIBLE;
3489  else
3490  *slatersetting = SCIP_SDPSLATERSETTING_PENALTYNOSLATER;
3491  break;
3492  case SCIP_SDPSLATER_HOLDS:
3493  switch( sdpi->dualslater )/*lint --e{788}*/
3494  {
3495  case SCIP_SDPSLATER_NOINFO:
3496  *slatersetting = SCIP_SDPSLATERSETTING_NOINFO;
3497  break;
3498  case SCIP_SDPSLATER_NOT:
3499  *slatersetting = SCIP_SDPSLATERSETTING_PENALTYNOSLATER;
3500  break;
3501  case SCIP_SDPSLATER_HOLDS:
3502  *slatersetting = SCIP_SDPSLATERSETTING_PENALTYWSLATER;
3503  break;
3504  case SCIP_SDPSLATER_INF:
3505  *slatersetting = SCIP_SDPSLATERSETTING_PENALTYINFEASIBLE;
3506  break;
3507  default:
3508  *slatersetting = SCIP_SDPSLATERSETTING_NOINFO;
3509  break;
3510  }
3511  break;
3512  default:
3513  *slatersetting = SCIP_SDPSLATERSETTING_NOINFO;
3514  break;
3515  }
3516  return SCIP_OKAY;
3517  }
3518 
3519  switch( sdpi->primalslater )/*lint --e{788}*/
3520  {
3521  case SCIP_SDPSLATER_NOINFO:
3522  if ( sdpi->dualslater == SCIP_SDPSLATER_NOT )
3523  {
3524  usedsetting = SCIP_SDPSOLVERSETTING_UNSOLVED;
3525  SCIP_CALL( SCIPsdpiSolverSettingsUsed(sdpi->sdpisolver, &usedsetting) );
3526  switch( usedsetting )/*lint --e{788}*/
3527  {
3529  *slatersetting = SCIP_SDPSLATERSETTING_STABLENOSLATER;
3530  break;
3533  *slatersetting = SCIP_SDPSLATERSETTING_UNSTABLENOSLATER;
3534  break;
3535  default:
3536  *slatersetting = SCIP_SDPSLATERSETTING_NOINFO;
3537  break;
3538  }
3539  }
3540  if ( sdpi->dualslater == SCIP_SDPSLATER_INF )
3541  {
3542  usedsetting = SCIP_SDPSOLVERSETTING_UNSOLVED;
3543  SCIP_CALL( SCIPsdpiSolverSettingsUsed(sdpi->sdpisolver, &usedsetting) );
3544  switch( usedsetting )/*lint --e{788}*/
3545  {
3547  *slatersetting = SCIP_SDPSLATERSETTING_STABLEINFEASIBLE;
3548  break;
3552  break;
3553  default:
3554  *slatersetting = SCIP_SDPSLATERSETTING_NOINFO;
3555  break;
3556  }
3557  }
3558  else
3559  *slatersetting = SCIP_SDPSLATERSETTING_NOINFO;
3560  break;
3561  case SCIP_SDPSLATER_NOT:
3562  if ( sdpi->dualslater == SCIP_SDPSLATER_INF )
3563  {
3564  usedsetting = SCIP_SDPSOLVERSETTING_UNSOLVED;
3565  SCIP_CALL( SCIPsdpiSolverSettingsUsed(sdpi->sdpisolver, &usedsetting) );
3566  switch( usedsetting )/*lint --e{788}*/
3567  {
3569  *slatersetting = SCIP_SDPSLATERSETTING_STABLEINFEASIBLE;
3570  break;
3574  break;
3575  default:
3576  *slatersetting = SCIP_SDPSLATERSETTING_NOINFO;
3577  break;
3578  }
3579  }
3580  else
3581  {
3582  usedsetting = SCIP_SDPSOLVERSETTING_UNSOLVED;
3583  SCIP_CALL( SCIPsdpiSolverSettingsUsed(sdpi->sdpisolver, &usedsetting) );
3584  switch( usedsetting )/*lint --e{788}*/
3585  {
3587  *slatersetting = SCIP_SDPSLATERSETTING_STABLENOSLATER;
3588  break;
3591  *slatersetting = SCIP_SDPSLATERSETTING_UNSTABLENOSLATER;
3592  break;
3593  default:
3594  *slatersetting = SCIP_SDPSLATERSETTING_NOINFO;
3595  break;
3596  }
3597  }
3598  break;
3599  case SCIP_SDPSLATER_HOLDS:
3600  switch( sdpi->dualslater )/*lint --e{788}*/
3601  {
3602  case SCIP_SDPSLATER_NOINFO:
3603  *slatersetting = SCIP_SDPSLATERSETTING_NOINFO;
3604  break;
3605  case SCIP_SDPSLATER_NOT:
3606  usedsetting = SCIP_SDPSOLVERSETTING_UNSOLVED;
3607  SCIP_CALL( SCIPsdpiSolverSettingsUsed(sdpi->sdpisolver, &usedsetting) );
3608  switch( usedsetting )/*lint --e{788}*/
3609  {
3611  *slatersetting = SCIP_SDPSLATERSETTING_STABLENOSLATER;
3612  break;
3615  *slatersetting = SCIP_SDPSLATERSETTING_UNSTABLENOSLATER;
3616  break;
3617  default:
3618  *slatersetting = SCIP_SDPSLATERSETTING_NOINFO;
3619  break;
3620  }
3621  break;
3622  case SCIP_SDPSLATER_INF:
3623  usedsetting = SCIP_SDPSOLVERSETTING_UNSOLVED;
3624  SCIP_CALL( SCIPsdpiSolverSettingsUsed(sdpi->sdpisolver, &usedsetting) );
3625  switch( usedsetting )/*lint --e{788}*/
3626  {
3628  *slatersetting = SCIP_SDPSLATERSETTING_STABLEINFEASIBLE;
3629  break;
3633  break;
3634  default:
3635  *slatersetting = SCIP_SDPSLATERSETTING_NOINFO;
3636  break;
3637  }
3638  break;
3639  case SCIP_SDPSLATER_HOLDS:
3640  usedsetting = SCIP_SDPSOLVERSETTING_UNSOLVED;
3641  SCIP_CALL( SCIPsdpiSolverSettingsUsed(sdpi->sdpisolver, &usedsetting) );
3642  switch( usedsetting )/*lint --e{788}*/
3643  {
3645  *slatersetting = SCIP_SDPSLATERSETTING_STABLEWSLATER;
3646  break;
3649  *slatersetting = SCIP_SDPSLATERSETTING_UNSTABLEWSLATER;
3650  break;
3651  default:
3652  *slatersetting = SCIP_SDPSLATERSETTING_NOINFO;
3653  break;
3654  }
3655  break;
3656  default:
3657  *slatersetting = SCIP_SDPSLATERSETTING_NOINFO;
3658  break;
3659  }
3660  break;
3661  default:
3662  *slatersetting = SCIP_SDPSLATERSETTING_NOINFO;
3663  break;
3664  }
3665 
3666  return SCIP_OKAY;
3667 }
3668 
3670 SCIP_RETCODE SCIPsdpiSlater(
3671  SCIP_SDPI* sdpi,
3672  SCIP_SDPSLATER* primalslater,
3673  SCIP_SDPSLATER* dualslater
3674  )
3675 {
3676  assert( sdpi != NULL );
3677  assert( primalslater != NULL );
3678  assert( dualslater != NULL );
3679 
3680 
3681  if ( sdpi->infeasible )
3682  {
3683  *primalslater = SCIP_SDPSLATER_NOINFO;
3684  *dualslater = sdpi->dualslater;
3685  return SCIP_OKAY;
3686  }
3687 
3688  if (sdpi->allfixed )
3689  {
3690  *primalslater = SCIP_SDPSLATER_NOINFO;
3691  *dualslater = SCIP_SDPSLATER_NOINFO;
3692  return SCIP_OKAY;
3693  }
3694 
3695  *primalslater = sdpi->primalslater;
3696  *dualslater = sdpi->dualslater;
3697 
3698  return SCIP_OKAY;
3699 }
3700 
3706 /*
3707  * Numerical Methods
3708  */
3709 
3715  SCIP_SDPI* sdpi
3716  )
3717 {
3718  assert( sdpi != NULL );
3719 
3720  return SCIPsdpiSolverInfinity(sdpi->sdpisolver);
3721 }
3722 
3725  SCIP_SDPI* sdpi,
3726  SCIP_Real val
3727  )
3728 {
3729  assert( sdpi != NULL );
3730 
3731  return ((val <= -SCIPsdpiInfinity(sdpi)) || (val >= SCIPsdpiInfinity(sdpi)));
3732 }
3733 
3735 SCIP_RETCODE SCIPsdpiGetRealpar(
3736  SCIP_SDPI* sdpi,
3737  SCIP_SDPPARAM type,
3738  SCIP_Real* dval
3739  )
3740 {
3741  assert( sdpi != NULL );
3742  assert( sdpi->sdpisolver != NULL );
3743  assert( dval != NULL );
3744 
3745  switch( type )/*lint --e{788}*/
3746  {
3747  case SCIP_SDPPAR_EPSILON:
3748  *dval = sdpi->epsilon;
3749  break;
3750  case SCIP_SDPPAR_FEASTOL:
3751  *dval = sdpi->feastol;
3752  break;
3753  case SCIP_SDPPAR_OBJLIMIT:
3754  SCIP_CALL_PARAM( SCIPsdpiSolverGetRealpar(sdpi->sdpisolver, type, dval) );
3755  break;
3757  *dval = sdpi->penaltyparam;
3758  break;
3760  *dval = sdpi->maxpenaltyparam;
3761  break;
3763  SCIP_CALL_PARAM( SCIPsdpiSolverGetRealpar(sdpi->sdpisolver, type, dval) );
3764  break;
3765  default:
3766  return SCIP_PARAMETERUNKNOWN;
3767  }
3768 
3769 #ifndef NDEBUG
3770  {
3771  SCIP_Real val;
3772  SCIP_CALL_PARAM( SCIPsdpiSolverGetRealpar(sdpi->sdpisolver, type, &val) );
3773  assert( REALABS(*dval - val) < sdpi->epsilon );
3774  }
3775 #endif
3776 
3777  return SCIP_OKAY;
3778 }
3779 
3781 SCIP_RETCODE SCIPsdpiSetRealpar(
3782  SCIP_SDPI* sdpi,
3783  SCIP_SDPPARAM type,
3784  SCIP_Real dval
3785  )
3786 {
3787  assert( sdpi != NULL );
3788 
3789  switch( type )/*lint --e{788}*/
3790  {
3791  case SCIP_SDPPAR_EPSILON:
3792  sdpi->epsilon = dval;
3793  SCIP_CALL_PARAM( SCIPsdpiSolverSetRealpar(sdpi->sdpisolver, type, dval) );
3794  break;
3795  case SCIP_SDPPAR_FEASTOL:
3796  sdpi->feastol = dval;
3797  SCIP_CALL_PARAM( SCIPsdpiSolverSetRealpar(sdpi->sdpisolver, type, dval) );
3798  break;
3799  case SCIP_SDPPAR_OBJLIMIT:
3800  SCIP_CALL_PARAM( SCIPsdpiSolverSetRealpar(sdpi->sdpisolver, type, dval) );
3801  break;
3803  sdpi->penaltyparam = dval;
3804  SCIP_CALL_PARAM( SCIPsdpiSolverSetRealpar(sdpi->sdpisolver, type, dval) );
3805  break;
3807  sdpi->maxpenaltyparam = dval;
3808  break;
3810  SCIP_CALL_PARAM( SCIPsdpiSolverSetRealpar(sdpi->sdpisolver, type, dval) );
3811  break;
3812  default:
3813  return SCIP_PARAMETERUNKNOWN;
3814  }
3815 
3816  return SCIP_OKAY;
3817 }
3818 
3820 SCIP_RETCODE SCIPsdpiGetIntpar(
3821  SCIP_SDPI* sdpi,
3822  SCIP_SDPPARAM type,
3823  int* ival
3824  )
3825 {
3826  assert( sdpi != NULL );
3827  assert( sdpi->sdpisolver != NULL );
3828  assert( ival != NULL );
3829 
3830  switch( type )/*lint --e{788}*/
3831  {
3832  case SCIP_SDPPAR_SDPINFO:
3833  SCIP_CALL_PARAM( SCIPsdpiSolverGetIntpar(sdpi->sdpisolver, type, ival) );
3834  break;
3836  *ival = sdpi->slatercheck;
3837  break;
3838  default:
3839  return SCIP_PARAMETERUNKNOWN;
3840  }
3841 
3842 #ifndef NDEBUG
3843  {
3844  if ( type != SCIP_SDPPAR_SLATERCHECK )
3845  {
3846  int val;
3847  SCIP_CALL_PARAM( SCIPsdpiSolverGetIntpar(sdpi->sdpisolver, type, &val) );
3848  assert( *ival == val );
3849  }
3850  }
3851 #endif
3852 
3853  return SCIP_OKAY;
3854 }
3855 
3857 SCIP_RETCODE SCIPsdpiSetIntpar(
3858  SCIP_SDPI* sdpi,
3859  SCIP_SDPPARAM type,
3860  int ival
3861  )
3862 {
3863  assert( sdpi != NULL );
3864  assert( sdpi->sdpisolver != NULL );
3865 
3866  switch( type )/*lint --e{788}*/
3867  {
3868  case SCIP_SDPPAR_SDPINFO:
3869  assert( ival == 0 || ival == 1 ); /* this is a boolean parameter */
3870  SCIP_CALL_PARAM( SCIPsdpiSolverSetIntpar(sdpi->sdpisolver, type, ival) );
3871  break;
3873  sdpi->slatercheck = ival;
3874  break;
3875  default:
3876  return SCIP_PARAMETERUNKNOWN;
3877  }
3878 
3879 #ifndef NDEBUG
3880  {
3881  if ( type != SCIP_SDPPAR_SLATERCHECK )
3882  {
3883  int val;
3884  SCIP_CALL_PARAM( SCIPsdpiSolverGetIntpar(sdpi->sdpisolver, type, &val) );
3885  assert( ival == val );
3886  }
3887  }
3888 #endif
3889 
3890  return SCIP_OKAY;
3891 }
3892 
3895  SCIP_SDPI* sdpi,
3896  SCIP_Real maxguess
3897  )
3898 {
3899  return SCIPsdpiSolverComputeLambdastar(sdpi->sdpisolver, maxguess);
3900 }
3901 
3904  SCIP_SDPI* sdpi,
3905  SCIP_Real maxcoeff,
3906  SCIP_Real* penaltyparam
3907  )
3908 {
3909  SCIP_CALL( SCIPsdpiSolverComputePenaltyparam(sdpi->sdpisolver, maxcoeff, penaltyparam) );
3910 
3911  sdpi->penaltyparam = *penaltyparam;
3912 
3913  return SCIP_OKAY;
3914 }
3915 
3918  SCIP_SDPI* sdpi,
3919  SCIP_Real penaltyparam,
3920  SCIP_Real* maxpenaltyparam
3921  )
3922 {
3923  SCIP_CALL( SCIPsdpiSolverComputeMaxPenaltyparam(sdpi->sdpisolver, penaltyparam, maxpenaltyparam) );
3924 
3925  sdpi->maxpenaltyparam = *maxpenaltyparam;
3926 
3927  /* if the initial penalty parameter is smaller than the maximum one, we decrease the initial correspondingly */
3928  /* if the maximum penalty parameter is smaller than the initial penalty paramater, we decrease the initial one correspondingly */
3929  if ( sdpi->penaltyparam > *maxpenaltyparam )
3930  {
3931  SCIPdebugMessage("Decreasing penaltyparameter of %f to maximum penalty paramater of %f.\n", sdpi->penaltyparam, *maxpenaltyparam);
3932  sdpi->penaltyparam = *maxpenaltyparam;
3933  }
3934 
3935  return SCIP_OKAY;
3936 }
3937 
3943 /*
3944  * File Interface Methods
3945  */
3946 
3951 SCIP_RETCODE SCIPsdpiReadSDP(
3952  SCIP_SDPI* sdpi,
3953  const char* fname
3954  )
3955 {/*lint --e{715}*/
3956  SCIPdebugMessage("Not implemented yet\n");
3957  return SCIP_LPERROR;
3958 }
3959 
3961 SCIP_RETCODE SCIPsdpiWriteSDP(
3962  SCIP_SDPI* sdpi,
3963  const char* fname
3964  )
3965 {/*lint --e{715}*/
3966  SCIPdebugMessage("Not implemented yet\n");
3967  return SCIP_LPERROR;
3968 }
3969 
SCIP_RETCODE SCIPsdpiFree(SCIP_SDPI **sdpi)
Definition: sdpi.c:1454
SCIP_Bool SCIPsdpiIsDualUnbounded(SCIP_SDPI *sdpi)
Definition: sdpi.c:2886
EXTERN SCIP_RETCODE SCIPsdpiSolverIncreaseCounter(SCIP_SDPISOLVER *sdpisolver)
EXTERN SCIP_RETCODE SCIPsdpiSolverGetSdpCalls(SCIP_SDPISOLVER *sdpisolver, int *calls)
SCIP_RETCODE SCIPsdpiDelLPRows(SCIP_SDPI *sdpi, int firstrow, int lastrow)
Definition: sdpi.c:1923
EXTERN SCIP_RETCODE SCIPsdpiSolverGetSolFeasibility(SCIP_SDPISOLVER *sdpisolver, SCIP_Bool *primalfeasible, SCIP_Bool *dualfeasible)
SCIP_RETCODE SCIPsdpiChgLPLhRhSides(SCIP_SDPI *sdpi, int nrows, const int *ind, const SCIP_Real *lhs, const SCIP_Real *rhs)
Definition: sdpi.c:2154
EXTERN SCIP_RETCODE SCIPsdpiSolverSetRealpar(SCIP_SDPISOLVER *sdpisolver, SCIP_SDPPARAM type, SCIP_Real dval)
#define DEFAULT_SDPSOLVEREPSILON
Definition: sdpi.c:119
SCIP_RETCODE SCIPsdpiGetSdpCalls(SCIP_SDPI *sdpi, int *calls)
Definition: sdpi.c:3314
EXTERN SCIP_Bool SCIPsdpiSolverIsObjlimExc(SCIP_SDPISOLVER *sdpisolver)
#define BMS_CALL(x)
Definition: sdpi.c:57
SCIP_RETCODE SCIPsdpiGetSolFeasibility(SCIP_SDPI *sdpi, SCIP_Bool *primalfeasible, SCIP_Bool *dualfeasible)
Definition: sdpi.c:2788
SCIP_RETCODE SCIPsdpiWriteSDP(SCIP_SDPI *sdpi, const char *fname)
Definition: sdpi.c:3961
EXTERN SCIP_Bool SCIPsdpiSolverIsAcceptable(SCIP_SDPISOLVER *sdpisolver)
static SCIP_RETCODE checkAllFixed(SCIP_SDPI *sdpi)
Definition: sdpi.c:830
SCIP_RETCODE SCIPsdpiGetLPNNonz(SCIP_SDPI *sdpi, int *nnonz)
Definition: sdpi.c:2268
EXTERN SCIP_RETCODE SCIPsdpiSolverResetCounter(SCIP_SDPISOLVER *sdpisolver)
EXTERN SCIP_Bool SCIPsdpiSolverFeasibilityKnown(SCIP_SDPISOLVER *sdpisolver)
EXTERN SCIP_Bool SCIPsdpiSolverIsConverged(SCIP_SDPISOLVER *sdpisolver)
#define MIN_EPSILON
Definition: sdpi.c:117
EXTERN SCIP_RETCODE SCIPsdpiSolverGetPrimalBoundVars(SCIP_SDPISOLVER *sdpisolver, SCIP_Real *lbvars, SCIP_Real *ubvars, int *arraylength)
enum SCIP_SDPSolverSetting SCIP_SDPSOLVERSETTING
Definition: type_sdpi.h:74
SCIP_Bool SCIPsdpiIsOptimal(SCIP_SDPI *sdpi)
Definition: sdpi.c:3081
SCIP_RETCODE SCIPsdpVarfixerMergeArraysIntoNew(BMS_BLKMEM *blkmem, SCIP_Real feastol, int *firstrow, int *firstcol, SCIP_Real *firstval, int firstlength, int *secondrow, int *secondcol, SCIP_Real *secondval, int secondlength, int *targetrow, int *targetcol, SCIP_Real *targetval, int *targetlength)
Definition: SdpVarfixer.c:255
SCIP_RETCODE SCIPsdpiGetIntpar(SCIP_SDPI *sdpi, SCIP_SDPPARAM type, int *ival)
Definition: sdpi.c:3820
SCIP_RETCODE SCIPsdpiGetSDPNNonz(SCIP_SDPI *sdpi, int *nnonz)
Definition: sdpi.c:2240
SCIP_Bool SCIPsdpiIsInfinity(SCIP_SDPI *sdpi, SCIP_Real val)
Definition: sdpi.c:3724
const char * SCIPsdpiGetSolverName(void)
Definition: sdpi.c:1351
EXTERN SCIP_RETCODE SCIPsdpiSolverFree(SCIP_SDPISOLVER **sdpisolver)
EXTERN SCIP_RETCODE SCIPsdpiSolverComputeMaxPenaltyparam(SCIP_SDPISOLVER *sdpisolver, SCIP_Real penaltyparam, SCIP_Real *maxpenaltyparam)
SCIP_RETCODE SCIPsdpiGetNSDPBlocks(SCIP_SDPI *sdpi, int *nsdpblocks)
Definition: sdpi.c:2212
SCIP_RETCODE SCIPsdpiGetSol(SCIP_SDPI *sdpi, SCIP_Real *objval, SCIP_Real *dualsol, int *dualsollength)
Definition: sdpi.c:3214
interface methods for specific SDP-solvers
SCIP_Bool SCIPsdpiIsPrimalInfeasible(SCIP_SDPI *sdpi)
Definition: sdpi.c:2840
SCIP_Bool SCIPsdpiFeasibilityKnown(SCIP_SDPI *sdpi)
Definition: sdpi.c:2774
SCIP_RETCODE SCIPsdpiLoadSDP(SCIP_SDPI *sdpi, int nvars, SCIP_Real *obj, SCIP_Real *lb, SCIP_Real *ub, int nsdpblocks, int *sdpblocksizes, int *sdpnblockvars, int sdpconstnnonz, int *sdpconstnblocknonz, int **sdpconstrow, int **sdpconstcol, SCIP_Real **sdpconstval, int sdpnnonz, int **sdpnblockvarnonz, int **sdpvar, int ***sdprow, int ***sdpcol, SCIP_Real ***sdpval, int nlpcons, SCIP_Real *lplhs, SCIP_Real *lprhs, int lpnnonz, int *lprow, int *lpcol, SCIP_Real *lpval)
Definition: sdpi.c:1638
SCIP_RETCODE SCIPsdpiComputeLambdastar(SCIP_SDPI *sdpi, SCIP_Real maxguess)
Definition: sdpi.c:3894
EXTERN SCIP_Bool SCIPsdpiSolverWasSolved(SCIP_SDPISOLVER *sdpisolver)
SCIP_RETCODE SCIPsdpiGetIterations(SCIP_SDPI *sdpi, int *iterations)
Definition: sdpi.c:3300
SCIP_RETCODE SCIPsdpiSettingsUsed(SCIP_SDPI *sdpi, SCIP_SDPSOLVERSETTING *usedsetting)
Definition: sdpi.c:3328
EXTERN SCIP_RETCODE SCIPsdpiSolverComputePenaltyparam(SCIP_SDPISOLVER *sdpisolver, SCIP_Real maxcoeff, SCIP_Real *penaltyparam)
EXTERN SCIP_Bool SCIPsdpiSolverIsDualFeasible(SCIP_SDPISOLVER *sdpisolver)
SCIP_RETCODE SCIPsdpiSlaterSettings(SCIP_SDPI *sdpi, SCIP_SDPSLATERSETTING *slatersetting)
Definition: sdpi.c:3365
EXTERN SCIP_Bool SCIPsdpiSolverIsOptimal(SCIP_SDPISOLVER *sdpisolver)
static SCIP_RETCODE findEmptyRowColsSDP(SCIP_SDPI *sdpi, int *sdpconstnblocknonz, int **sdpconstrow, int **sdpconstcol, SCIP_Real **sdpconstval, int **indchanges, int *nremovedinds, int *blockindchanges, int *nremovedblocks)
Definition: sdpi.c:356
SCIP_Bool SCIPsdpiIsAcceptable(SCIP_SDPI *sdpi)
Definition: sdpi.c:3104
EXTERN SCIP_Bool SCIPsdpiSolverIsPrimalUnbounded(SCIP_SDPISOLVER *sdpisolver)
EXTERN int SCIPsdpiSolverGetInternalStatus(SCIP_SDPISOLVER *sdpisolver)
SCIP_Bool SCIPsdpiIsIterlimExc(SCIP_SDPI *sdpi)
Definition: sdpi.c:2998
SCIP_Bool SCIPsdpiIsTimelimExc(SCIP_SDPI *sdpi)
Definition: sdpi.c:3020
SCIP_Bool SCIPsdpiIsDualInfeasible(SCIP_SDPI *sdpi)
Definition: sdpi.c:2909
General interface methods for SDP-preprocessing (mainly fixing variables and removing empty rows/cols...
SCIP_RETCODE SCIPsdpiGetConstNNonz(SCIP_SDPI *sdpi, int *nnonz)
Definition: sdpi.c:2254
enum SCIP_SDPSlaterSetting SCIP_SDPSLATERSETTING
Definition: type_sdpi.h:96
SCIP_RETCODE SCIPsdpiClone(SCIP_SDPI *oldsdpi, SCIP_SDPI *newsdpi)
Definition: sdpi.c:1519
EXTERN SCIP_RETCODE SCIPsdpiSolverGetIterations(SCIP_SDPISOLVER *sdpisolver, int *iterations)
EXTERN SCIP_RETCODE SCIPsdpiSolverSetIntpar(SCIP_SDPISOLVER *sdpisolver, SCIP_SDPPARAM type, int ival)
SCIP_RETCODE SCIPsdpiChgBounds(SCIP_SDPI *sdpi, int nvars, const int *ind, const SCIP_Real *lb, const SCIP_Real *ub)
Definition: sdpi.c:2120
EXTERN const char * SCIPsdpiSolverGetSolverDesc(void)
EXTERN SCIP_RETCODE SCIPsdpiSolverGetIntpar(SCIP_SDPISOLVER *sdpisolver, SCIP_SDPPARAM type, int *ival)
SCIP_RETCODE SCIPsdpiDelLPRowset(SCIP_SDPI *sdpi, int *dstat)
Definition: sdpi.c:2033
EXTERN SCIP_Bool SCIPsdpiSolverIsDualInfeasible(SCIP_SDPISOLVER *sdpisolver)
EXTERN const char * SCIPsdpiSolverGetSolverName(void)
SCIP_RETCODE SCIPsdpiGetLowerObjbound(SCIP_SDPI *sdpi, SCIP_Real *objlb)
Definition: sdpi.c:3165
SCIP_Bool SCIPsdpiIsObjlimExc(SCIP_SDPI *sdpi)
Definition: sdpi.c:2976
SCIP_RETCODE SCIPsdpiGetObj(SCIP_SDPI *sdpi, int firstvar, int lastvar, SCIP_Real *vals)
Definition: sdpi.c:2282
void * SCIPsdpiGetSolverPointer(SCIP_SDPI *sdpi)
Definition: sdpi.c:1372
int SCIPsdpiGetInternalStatus(SCIP_SDPI *sdpi)
Definition: sdpi.c:3055
static SCIP_RETCODE checkFixedFeasibilitySdp(SCIP_SDPI *sdpi, int *sdpconstnblocknonz, int **sdpconstrow, int **sdpconstcol, SCIP_Real **sdpconstval, int **indchanges, int *nremovedinds, int *blockindchanges)
Definition: sdpi.c:858
SCIP_RETCODE SCIPsdpiCreate(SCIP_SDPI **sdpi, SCIP_MESSAGEHDLR *messagehdlr, BMS_BLKMEM *blkmem)
Definition: sdpi.c:1390
EXTERN SCIP_Bool SCIPsdpiSolverIsPrimalInfeasible(SCIP_SDPISOLVER *sdpisolver)
SCIP_RETCODE SCIPsdpiAddLPRows(SCIP_SDPI *sdpi, int nrows, const SCIP_Real *lhs, const SCIP_Real *rhs, int nnonz, const int *row, const int *col, const SCIP_Real *val)
Definition: sdpi.c:1858
SCIP_RETCODE SCIPsdpiGetNVars(SCIP_SDPI *sdpi, int *nvars)
Definition: sdpi.c:2226
const char * SCIPsdpiGetSolverDesc(void)
Definition: sdpi.c:1359
SCIP_RETCODE SCIPsdpiComputePenaltyparam(SCIP_SDPI *sdpi, SCIP_Real maxcoeff, SCIP_Real *penaltyparam)
Definition: sdpi.c:3903
SCIP_RETCODE SCIPsdpiSetIntpar(SCIP_SDPI *sdpi, SCIP_SDPPARAM type, int ival)
Definition: sdpi.c:3857
EXTERN SCIP_RETCODE SCIPsdpiSolverSettingsUsed(SCIP_SDPISOLVER *sdpisolver, SCIP_SDPSOLVERSETTING *usedsetting)
SCIP_Bool SCIPsdpiIsPrimalUnbounded(SCIP_SDPI *sdpi)
Definition: sdpi.c:2817
SCIP_Real SCIPsdpiInfinity(SCIP_SDPI *sdpi)
Definition: sdpi.c:3714
#define CHECK_IF_SOLVED_BOOL(sdpi)
Definition: sdpi.c:79
SCIP_RETCODE SCIPsdpiSolve(SCIP_SDPI *sdpi, SCIP_Real *start, SCIP_SDPSOLVERSETTING startsettings, SCIP_Bool enforceslatercheck, SCIP_Real timelimit)
Definition: sdpi.c:2388
EXTERN SCIP_Bool SCIPsdpiSolverIsIterlimExc(SCIP_SDPISOLVER *sdpisolver)
SCIP_RETCODE SCIPsdpiGetRhSides(SCIP_SDPI *sdpi, int firstrow, int lastrow, SCIP_Real *rhss)
Definition: sdpi.c:2354
#define DUPLICATE_ARRAY_NULL(blkmem, target, source, size)
Definition: sdpi.c:90
adds the main functionality to fix/unfix/(multi-)aggregate variables by merging two three-tuple-array...
static void ensureLowerTriangular(int *i, int *j)
Definition: sdpi.c:193
EXTERN SCIP_RETCODE SCIPsdpiSolverLoadAndSolve(SCIP_SDPISOLVER *sdpisolver, int nvars, SCIP_Real *obj, SCIP_Real *lb, SCIP_Real *ub, int nsdpblocks, int *sdpblocksizes, int *sdpnblockvars, int sdpconstnnonz, int *sdpconstnblocknonz, int **sdpconstrow, int **sdpconstcol, SCIP_Real **sdpconstval, int sdpnnonz, int **sdpnblockvarnonz, int **sdpvar, int ***sdprow, int ***sdpcol, SCIP_Real ***sdpval, int **indchanges, int *nremovedinds, int *blockindchanges, int nremovedblocks, int nlpcons, int noldlpcons, SCIP_Real *lplhs, SCIP_Real *lprhs, int *rownactivevars, int lpnnonz, int *lprow, int *lpcol, SCIP_Real *lpval, SCIP_Real *start, SCIP_SDPSOLVERSETTING startsettings, SCIP_Real timelimit)
SCIP_RETCODE SCIPsdpiGetObjval(SCIP_SDPI *sdpi, SCIP_Real *objval)
Definition: sdpi.c:3130
EXTERN SCIP_RETCODE SCIPsdpiSolverGetRealpar(SCIP_SDPISOLVER *sdpisolver, SCIP_SDPPARAM type, SCIP_Real *dval)
#define NINCREASESGAMMA
Definition: sdpi.c:116
SCIP_Bool SCIPsdpiIsConverged(SCIP_SDPI *sdpi)
Definition: sdpi.c:2954
static SCIP_Bool isFixed(SCIP_SDPI *sdpi, int v)
Definition: sdpi.c:210
#define DEFAULT_MAXPENALTYPARAM
Definition: sdpi.c:122
EXTERN SCIP_Bool SCIPsdpiSolverIsTimelimExc(SCIP_SDPISOLVER *sdpisolver)
SCIP_Bool SCIPsdpiWasSolved(SCIP_SDPI *sdpi)
Definition: sdpi.c:2752
SCIP_RETCODE SCIPsdpiReadSDP(SCIP_SDPI *sdpi, const char *fname)
Definition: sdpi.c:3951
SCIP_RETCODE SCIPsdpiComputeMaxPenaltyparam(SCIP_SDPI *sdpi, SCIP_Real penaltyparam, SCIP_Real *maxpenaltyparam)
Definition: sdpi.c:3917
SCIP_RETCODE SCIPsdpiClear(SCIP_SDPI *sdpi)
Definition: sdpi.c:2075
SCIP_RETCODE SCIPsdpiGetBounds(SCIP_SDPI *sdpi, int firstvar, int lastvar, SCIP_Real *lbs, SCIP_Real *ubs)
Definition: sdpi.c:2304
EXTERN SCIP_RETCODE SCIPsdpiSolverGetObjval(SCIP_SDPISOLVER *sdpisolver, SCIP_Real *objval)
SCIP_RETCODE SCIPsdpiChgObj(SCIP_SDPI *sdpi, int nvars, const int *ind, const SCIP_Real *obj)
Definition: sdpi.c:2091
EXTERN SCIP_Bool SCIPsdpiSolverIsDualUnbounded(SCIP_SDPISOLVER *sdpisolver)
#define DEFAULT_PENALTYPARAM
Definition: sdpi.c:121
SCIP_Bool SCIPsdpiIsDualFeasible(SCIP_SDPI *sdpi)
Definition: sdpi.c:2932
struct SCIP_SDPi SCIP_SDPI
Definition: type_sdpi.h:108
#define DEFAULT_SDPSOLVERFEASTOL
Definition: sdpi.c:120
EXTERN SCIP_RETCODE SCIPsdpiSolverGetSol(SCIP_SDPISOLVER *sdpisolver, SCIP_Real *objval, SCIP_Real *dualsol, int *dualsollength)
SCIP_Bool SCIPsdpiIsPrimalFeasible(SCIP_SDPI *sdpi)
Definition: sdpi.c:2863
SCIP_RETCODE SCIPsdpiSetRealpar(SCIP_SDPI *sdpi, SCIP_SDPPARAM type, SCIP_Real dval)
Definition: sdpi.c:3781
EXTERN SCIP_Bool SCIPsdpiSolverIsPrimalFeasible(SCIP_SDPISOLVER *sdpisolver)
enum SCIP_SDPSlater SCIP_SDPSLATER
Definition: type_sdpi.h:106
static SCIP_RETCODE checkSlaterCondition(SCIP_SDPI *sdpi, SCIP_Real timelimit, clock_t starttime, int *sdpconstnblocknonz, int **sdpconstrow, int **sdpconstcol, SCIP_Real **sdpconstval, int **indchanges, int *nremovedinds, SCIP_Real *lplhsafterfix, SCIP_Real *lprhsafterfix, int *rowsnactivevars, int *blockindchanges, int sdpconstnnonz, int nactivelpcons, int nremovedblocks, SCIP_Bool rootnodefailed)
Definition: sdpi.c:964
struct SCIP_SDPiSolver SCIP_SDPISOLVER
Definition: sdpisolver.h:70
SCIP_RETCODE SCIPsdpiGetRealpar(SCIP_SDPI *sdpi, SCIP_SDPPARAM type, SCIP_Real *dval)
Definition: sdpi.c:3735
EXTERN SCIP_RETCODE SCIPsdpiSolverCreate(SCIP_SDPISOLVER **sdpisolver, SCIP_MESSAGEHDLR *messagehdlr, BMS_BLKMEM *blkmem)
static SCIP_RETCODE compConstMatAfterFixings(SCIP_SDPI *sdpi, int *sdpconstnnonz, int *sdpconstnblocknonz, int **sdpconstrow, int **sdpconstcol, SCIP_Real **sdpconstval)
Definition: sdpi.c:242
#define CHECK_IF_SOLVED(sdpi)
Definition: sdpi.c:68
EXTERN SCIP_Real SCIPsdpiSolverInfinity(SCIP_SDPISOLVER *sdpisolver)
enum SCIP_SDPParam SCIP_SDPPARAM
Definition: type_sdpi.h:63
EXTERN void * SCIPsdpiSolverGetSolverPointer(SCIP_SDPISOLVER *sdpisolver)
EXTERN SCIP_Bool SCIPsdpiSolverIsInfinity(SCIP_SDPISOLVER *sdpisolver, SCIP_Real val)
EXTERN SCIP_RETCODE SCIPsdpiSolverLoadAndSolveWithPenalty(SCIP_SDPISOLVER *sdpisolver, SCIP_Real penaltyparam, SCIP_Bool withobj, SCIP_Bool rbound, int nvars, SCIP_Real *obj, SCIP_Real *lb, SCIP_Real *ub, int nsdpblocks, int *sdpblocksizes, int *sdpnblockvars, int sdpconstnnonz, int *sdpconstnblocknonz, int **sdpconstrow, int **sdpconstcol, SCIP_Real **sdpconstval, int sdpnnonz, int **sdpnblockvarnonz, int **sdpvar, int ***sdprow, int ***sdpcol, SCIP_Real ***sdpval, int **indchanges, int *nremovedinds, int *blockindchanges, int nremovedblocks, int nlpcons, int noldlpcons, SCIP_Real *lplhs, SCIP_Real *lprhs, int *rownactivevars, int lpnnonz, int *lprow, int *lpcol, SCIP_Real *lpval, SCIP_Real *start, SCIP_SDPSOLVERSETTING startsettings, SCIP_Real timelimit, SCIP_Bool *feasorig, SCIP_Bool *penaltybound)
SCIP_RETCODE SCIPsdpiGetNLPRows(SCIP_SDPI *sdpi, int *nlprows)
Definition: sdpi.c:2198
SCIP_RETCODE SCIPsdpiGetLhSides(SCIP_SDPI *sdpi, int firstrow, int lastrow, SCIP_Real *lhss)
Definition: sdpi.c:2332
SCIP_RETCODE SCIPsdpiGetPrimalBoundVars(SCIP_SDPI *sdpi, SCIP_Real *lbvars, SCIP_Real *ubvars, int *arraylength)
Definition: sdpi.c:3268
interface methods for eigenvector computation and matrix multiplication using different versions of L...
SCIP_Bool SCIPsdpiSolvedOrig(SCIP_SDPI *sdpi)
Definition: sdpi.c:2762
SCIP_RETCODE SCIPsdpiSlater(SCIP_SDPI *sdpi, SCIP_SDPSLATER *primalslater, SCIP_SDPSLATER *dualslater)
Definition: sdpi.c:3670
#define SCIP_CALL_PARAM(x)
Definition: sdpi.c:100
static SCIP_RETCODE computeLpLhsRhsAfterFixings(SCIP_SDPI *sdpi, int *nactivelpcons, SCIP_Real *lplhsafterfix, SCIP_Real *lprhsafterfix, int *rownactivevars, SCIP_Bool *fixingsfound)
Definition: sdpi.c:483
EXTERN SCIP_RETCODE SCIPsdpiSolverComputeLambdastar(SCIP_SDPISOLVER *sdpisolver, SCIP_Real maxguess)
EXTERN SCIP_RETCODE SCIPlapackComputeIthEigenvalue(BMS_BLKMEM *blkmem, SCIP_Bool geteigenvectors, int n, SCIP_Real *A, int i, SCIP_Real *eigenvalue, SCIP_Real *eigenvector)