Scippy

SoPlex

Sequential object-oriented simPlex

soplex.cpp
Go to the documentation of this file.
1 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
2 /* */
3 /* This file is part of the class library */
4 /* SoPlex --- the Sequential object-oriented simPlex. */
5 /* */
6 /* Copyright (C) 1996-2017 Konrad-Zuse-Zentrum */
7 /* fuer Informationstechnik Berlin */
8 /* */
9 /* SoPlex is distributed under the terms of the ZIB Academic Licence. */
10 /* */
11 /* You should have received a copy of the ZIB Academic License */
12 /* along with SoPlex; see the file COPYING. If not email to soplex@zib.de. */
13 /* */
14 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
15 
16 /**@file soplex.cpp
17  * @brief Preconfigured SoPlex LP solver
18  */
19 
20 #ifndef SOPLEX_LEGACY
21 #include <assert.h>
22 #include "limits.h"
23 #include <iostream>
24 
25 #ifndef _MSC_VER
26 #include <strings.h>
27 #endif
28 
29 #include "soplex.h"
30 #include "spxfileio.h"
31 #include "spxgithash.h"
32 #include "statistics.h"
33 #include "mpsinput.h"
34 
35 /// maximum length of lines in settings file
36 #define SET_MAX_LINE_LEN 500
37 /// default setting for LU refactorization interval
38 #define DEFAULT_REFACTOR_INTERVAL 200
39 
40 #ifdef _MSC_VER
41 #define strncasecmp _strnicmp
42 #endif
43 
44 namespace soplex
45 {
47  // should lifting be used to reduce range of nonzero matrix coefficients?
48  name[SoPlex::LIFTING] = "lifting";
49  description[SoPlex::LIFTING] = "should lifting be used to reduce range of nonzero matrix coefficients?";
51 
52  // should LP be transformed to equality form before a rational solve?
53  name[SoPlex::EQTRANS] = "eqtrans";
54  description[SoPlex::EQTRANS] = "should LP be transformed to equality form before a rational solve?";
56 
57  // should dual infeasibility be tested in order to try to return a dual solution even if primal infeasible?
58  name[SoPlex::TESTDUALINF] = "testdualinf";
59  description[SoPlex::TESTDUALINF] = "should dual infeasibility be tested in order to try to return a dual solution even if primal infeasible?";
61 
62  // should a rational factorization be performed after iterative refinement?
63  name[SoPlex::RATFAC] = "ratfac";
64  description[SoPlex::RATFAC] = "should a rational factorization be performed after iterative refinement?";
66 
67  // should the decomposition based dual simplex be used to solve the LP? Setting this to true forces the solve mode to
68  // SOLVEMODE_REAL and the basis representation to REPRESENTATION_ROW
69  name[SoPlex::USEDECOMPDUALSIMPLEX] = "decompositiondualsimplex";
70  description[SoPlex::USEDECOMPDUALSIMPLEX] = "should the decomposition based dual simplex be used to solve the LP?";
72 
73  // should the degeneracy be computed for each basis?
74  name[SoPlex::COMPUTEDEGEN] = "computedegen";
75  description[SoPlex::COMPUTEDEGEN] = "should the degeneracy be computed for each basis?";
77 
78  // should the dual of the complementary problem be used in the decomposition simplex?
79  name[SoPlex::USECOMPDUAL] = "usecompdual";
80  description[SoPlex::USECOMPDUAL] = "should the dual of the complementary problem be used in the decomposition simplex?";
82 
83  /// should row and bound violations be computed explicitly in the update of reduced problem in the decomposition
84  // simplex
85  name[SoPlex::EXPLICITVIOL] = "explicitviol";
86  description[SoPlex::EXPLICITVIOL] = "Should violations of the original problem be explicitly computed in the decomposition simplex?";
88 
89  // should cycling solutions be accepted during iterative refinement?
90  name[SoPlex::ACCEPTCYCLING] = "acceptcycling";
91  description[SoPlex::ACCEPTCYCLING] = "should cycling solutions be accepted during iterative refinement?";
93 
94  // apply rational reconstruction after each iterative refinement?
95  name[SoPlex::RATREC] = "ratrec";
96  description[SoPlex::RATREC] = "apply rational reconstruction after each iterative refinement?";
98 
99  // round scaling factors for iterative refinement to powers of two?
100  name[SoPlex::POWERSCALING] = "powerscaling";
101  description[SoPlex::POWERSCALING] = "round scaling factors for iterative refinement to powers of two?";
103 
104  // continue iterative refinement with exact basic solution if not optimal?
105  name[SoPlex::RATFACJUMP] = "ratfacjump";
106  description[SoPlex::RATFACJUMP] = "continue iterative refinement with exact basic solution if not optimal?";
108 
109  // use bound flipping also for row representation?
110  name[SoPlex::ROWBOUNDFLIPS] = "rowboundflips";
111  description[SoPlex::ROWBOUNDFLIPS] = "use bound flipping also for row representation?";
113 
114  // use persistent scaling?
115  name[SoPlex::PERSISTENTSCALING] = "persistentscaling";
116  description[SoPlex::PERSISTENTSCALING] = "should persistent scaling be used?";
118 
119  // perturb the entire problem or only the relevant bounds of s single pivot?
120  name[SoPlex::FULLPERTURBATION] = "fullperturbation";
121  description[SoPlex::FULLPERTURBATION] = "should perturbation be applied to the entire problem?";
123  }
124 
126  // objective sense
127  name[SoPlex::OBJSENSE] = "objsense";
128  description[SoPlex::OBJSENSE] = "objective sense (-1 - minimize, +1 - maximize)";
129  lower[SoPlex::OBJSENSE] = -1;
130  upper[SoPlex::OBJSENSE] = 1;
132 
133  // type of computational form, i.e., column or row representation
134  name[SoPlex::REPRESENTATION] = "representation";
135  description[SoPlex::REPRESENTATION] = "type of computational form (0 - auto, 1 - column representation, 2 - row representation)";
136  lower[SoPlex::REPRESENTATION] = 0;
137  upper[SoPlex::REPRESENTATION] = 2;
139 
140  // type of algorithm, i.e., primal or dual
141  name[SoPlex::ALGORITHM] = "algorithm";
142  description[SoPlex::ALGORITHM] = "type of algorithm (0 - primal, 1 - dual)";
143  lower[SoPlex::ALGORITHM] = 0;
144  upper[SoPlex::ALGORITHM] = 1;
146 
147  // type of LU update
148  name[SoPlex::FACTOR_UPDATE_TYPE] = "factor_update_type";
149  description[SoPlex::FACTOR_UPDATE_TYPE] = "type of LU update (0 - eta update, 1 - Forrest-Tomlin update)";
150  lower[SoPlex::FACTOR_UPDATE_TYPE] = 0;
151  upper[SoPlex::FACTOR_UPDATE_TYPE] = 1;
153 
154  // maximum number of updates without fresh factorization
155  name[SoPlex::FACTOR_UPDATE_MAX] = "factor_update_max";
156  description[SoPlex::FACTOR_UPDATE_MAX] = "maximum number of LU updates without fresh factorization (0 - auto)";
157  lower[SoPlex::FACTOR_UPDATE_MAX] = 0;
158  upper[SoPlex::FACTOR_UPDATE_MAX] = INT_MAX;
160 
161  // iteration limit (-1 if unlimited)
162  name[SoPlex::ITERLIMIT] = "iterlimit";
163  description[SoPlex::ITERLIMIT] = "iteration limit (-1 - no limit)";
164  lower[SoPlex::ITERLIMIT] = -1;
165  upper[SoPlex::ITERLIMIT] = INT_MAX;
167 
168  // refinement limit (-1 if unlimited)
169  name[SoPlex::REFLIMIT] = "reflimit";
170  description[SoPlex::REFLIMIT] = "refinement limit (-1 - no limit)";
171  lower[SoPlex::REFLIMIT] = -1;
172  upper[SoPlex::REFLIMIT] = INT_MAX;
174 
175  // stalling refinement limit (-1 if unlimited)
176  name[SoPlex::STALLREFLIMIT] = "stallreflimit";
177  description[SoPlex::STALLREFLIMIT] = "stalling refinement limit (-1 - no limit)";
178  lower[SoPlex::STALLREFLIMIT] = -1;
179  upper[SoPlex::STALLREFLIMIT] = INT_MAX;
181 
182  // display frequency
183  name[SoPlex::DISPLAYFREQ] = "displayfreq";
184  description[SoPlex::DISPLAYFREQ] = "display frequency";
185  lower[SoPlex::DISPLAYFREQ] = 1;
186  upper[SoPlex::DISPLAYFREQ] = INT_MAX;
188 
189  // verbosity level
190  name[SoPlex::VERBOSITY] = "verbosity";
191  description[SoPlex::VERBOSITY] = "verbosity level (0 - error, 1 - warning, 2 - debug, 3 - normal, 4 - high, 5 - full)";
192  lower[SoPlex::VERBOSITY] = 0;
193  upper[SoPlex::VERBOSITY] = 5;
195  //_intParamDefault[SoPlex::VERBOSITY] = SoPlex::VERBOSITY_FULL;
196 
197  // type of simplifier
198  name[SoPlex::SIMPLIFIER] = "simplifier";
199  description[SoPlex::SIMPLIFIER] = "simplifier (0 - off, 1 - auto)";
200  lower[SoPlex::SIMPLIFIER] = 0;
201  upper[SoPlex::SIMPLIFIER] = 1;
203 
204  // type of scaler
205  name[SoPlex::SCALER] = "scaler";
206  description[SoPlex::SCALER] = "scaling (0 - off, 1 - uni-equilibrium, 2 - bi-equilibrium, 3 - geometric, 4 - iterated geometric, 5 - least squares, 6 - geometric-equilibrium)";
207  lower[SoPlex::SCALER] = 0;
208  upper[SoPlex::SCALER] = 6;
210 
211  // type of starter used to create crash basis
212  name[SoPlex::STARTER] = "starter";
213  description[SoPlex::STARTER] = "crash basis generated when starting from scratch (0 - none, 1 - weight, 2 - sum, 3 - vector)";
214  lower[SoPlex::STARTER] = 0;
215  upper[SoPlex::STARTER] = 3;
217 
218  // type of pricer
219  name[SoPlex::PRICER] = "pricer";
220  description[SoPlex::PRICER] = "pricing method (0 - auto, 1 - dantzig, 2 - parmult, 3 - devex, 4 - quicksteep, 5 - steep)";
221  lower[SoPlex::PRICER] = 0;
222  upper[SoPlex::PRICER] = 5;
224 
225  // type of ratio test
226  name[SoPlex::RATIOTESTER] = "ratiotester";
227  description[SoPlex::RATIOTESTER] = "method for ratio test (0 - textbook, 1 - harris, 2 - fast, 3 - boundflipping)";
228  lower[SoPlex::RATIOTESTER] = 0;
229  upper[SoPlex::RATIOTESTER] = 3;
231 
232  // mode for synchronizing real and rational LP
233  name[SoPlex::SYNCMODE] = "syncmode";
234  description[SoPlex::SYNCMODE] = "mode for synchronizing real and rational LP (0 - store only real LP, 1 - auto, 2 - manual)";
235  lower[SoPlex::SYNCMODE] = 0;
236  upper[SoPlex::SYNCMODE] = 2;
238 
239  // mode for reading LP files
240  name[SoPlex::READMODE] = "readmode";
241  description[SoPlex::READMODE] = "mode for reading LP files (0 - floating-point, 1 - rational)";
242  lower[SoPlex::READMODE] = 0;
243  upper[SoPlex::READMODE] = 1;
245 
246  // mode for iterative refinement strategy
247  name[SoPlex::SOLVEMODE] = "solvemode";
248  description[SoPlex::SOLVEMODE] = "mode for iterative refinement strategy (0 - floating-point solve, 1 - auto, 2 - exact rational solve)";
249  lower[SoPlex::SOLVEMODE] = 0;
250  upper[SoPlex::SOLVEMODE] = 2;
252 
253  // mode for iterative refinement strategy
254  name[SoPlex::CHECKMODE] = "checkmode";
255  description[SoPlex::CHECKMODE] = "mode for a posteriori feasibility checks (0 - floating-point check, 1 - auto, 2 - exact rational check)";
256  lower[SoPlex::CHECKMODE] = 0;
257  upper[SoPlex::CHECKMODE] = 2;
259 
260  // type of timing
261  name[SoPlex::TIMER] = "timer";
262  description[SoPlex::TIMER] = "type of timer (1 - cputime, aka. usertime, 2 - wallclock time, 0 - no timing)";
263  lower[SoPlex::TIMER] = 0;
264  upper[SoPlex::TIMER] = 2;
266 
267  // mode for hyper sparse pricing
268  name[SoPlex::HYPER_PRICING] = "hyperpricing";
269  description[SoPlex::HYPER_PRICING] = "mode for hyper sparse pricing (0 - off, 1 - auto, 2 - always)";
270  lower[SoPlex::HYPER_PRICING] = 0;
271  upper[SoPlex::HYPER_PRICING] = 2;
273 
274  // minimum number of stalling refinements since last pivot to trigger rational factorization
275  name[SoPlex::RATFAC_MINSTALLS] = "ratfac_minstalls";
276  description[SoPlex::RATFAC_MINSTALLS] = "minimum number of stalling refinements since last pivot to trigger rational factorization";
277  lower[SoPlex::RATFAC_MINSTALLS] = 0;
278  upper[SoPlex::RATFAC_MINSTALLS] = INT_MAX;
280 
281  // maximum number of conjugate gradient iterations in least square scaling
282  name[SoPlex::LEASTSQ_MAXROUNDS] = "leastsq_maxrounds";
283  description[SoPlex::LEASTSQ_MAXROUNDS] = "maximum number of conjugate gradient iterations in least square scaling";
284  lower[SoPlex::LEASTSQ_MAXROUNDS] = 0;
285  upper[SoPlex::LEASTSQ_MAXROUNDS] = INT_MAX;
287 
288  // mode for solution polishing
289  name[SoPlex::SOLUTION_POLISHING] = "solution_polishing";
290  description[SoPlex::SOLUTION_POLISHING] = "mode for solution polishing (0 - off, 1 - max basic slack, 2 - min basic slack)";
291  lower[SoPlex::SOLUTION_POLISHING] = 0;
292  upper[SoPlex::SOLUTION_POLISHING] = 2;
294 
295  // the number of iterations before the decomposition simplex initialisation is terminated.
296  name[SoPlex::DECOMP_ITERLIMIT] = "decomp_iterlimit";
297  description[SoPlex::DECOMP_ITERLIMIT] = "the number of iterations before the decomposition simplex initialisation solve is terminated";
298  lower[SoPlex::DECOMP_ITERLIMIT] = 1;
299  upper[SoPlex::DECOMP_ITERLIMIT] = INT_MAX;
301 
302  // maximum number of violated rows added in each iteration of the decomposition simplex
303  name[SoPlex::DECOMP_MAXADDEDROWS] = "decomp_maxaddedrows";
304  description[SoPlex::DECOMP_MAXADDEDROWS] = "maximum number of rows that are added to the reduced problem when using the decomposition based simplex";
305  lower[SoPlex::DECOMP_MAXADDEDROWS] = 1;
306  upper[SoPlex::DECOMP_MAXADDEDROWS] = INT_MAX;
308 
309  // maximum number of violated rows added in each iteration of the decomposition simplex
310  name[SoPlex::DECOMP_DISPLAYFREQ] = "decomp_displayfreq";
311  description[SoPlex::DECOMP_DISPLAYFREQ] = "the frequency that the decomposition based simplex status output is displayed.";
312  lower[SoPlex::DECOMP_DISPLAYFREQ] = 1;
313  upper[SoPlex::DECOMP_DISPLAYFREQ] = INT_MAX;
315 
316  // the verbosity of the decomposition based simplex
317  name[SoPlex::DECOMP_VERBOSITY] = "decomp_verbosity";
318  description[SoPlex::DECOMP_VERBOSITY] = "the verbosity of decomposition based simplex (0 - error, 1 - warning, 2 - debug, 3 - normal, 4 - high, 5 - full).";
319  lower[SoPlex::DECOMP_VERBOSITY] = 1;
320  upper[SoPlex::DECOMP_VERBOSITY] = 5;
322 
323  // printing condition number during the solve
324  name[SoPlex::PRINTCONDITION] = "printcondition";
325  description[SoPlex::PRINTCONDITION] = "print condition number during the solve (0 - off, 1 - ratio estimate , 2 - sum estimate, 3 - product estimate, 4 - exact)";
326  lower[SoPlex::PRINTCONDITION] = 0;
327  upper[SoPlex::PRINTCONDITION] = 4;
329  }
330 
332  // primal feasibility tolerance
333  name[SoPlex::FEASTOL] = "feastol";
334  description[SoPlex::FEASTOL] = "primal feasibility tolerance";
335  lower[SoPlex::FEASTOL] = 0.0;
336  upper[SoPlex::FEASTOL] = 1.0;
338 
339  // dual feasibility tolerance
340  name[SoPlex::OPTTOL] = "opttol";
341  description[SoPlex::OPTTOL] = "dual feasibility tolerance";
342  lower[SoPlex::OPTTOL] = 0.0;
343  upper[SoPlex::OPTTOL] = 1.0;
345 
346  ///@todo define suitable values depending on Real type
347  // general zero tolerance
348  name[SoPlex::EPSILON_ZERO] = "epsilon_zero";
349  description[SoPlex::EPSILON_ZERO] = "general zero tolerance";
350  lower[SoPlex::EPSILON_ZERO] = 0.0;
351  upper[SoPlex::EPSILON_ZERO] = 1.0;
353 
354  ///@todo define suitable values depending on Real type
355  // zero tolerance used in factorization
356  name[SoPlex::EPSILON_FACTORIZATION] = "epsilon_factorization";
357  description[SoPlex::EPSILON_FACTORIZATION] = "zero tolerance used in factorization";
358  lower[SoPlex::EPSILON_FACTORIZATION] = 0.0;
359  upper[SoPlex::EPSILON_FACTORIZATION] = 1.0;
361 
362  ///@todo define suitable values depending on Real type
363  // zero tolerance used in update of the factorization
364  name[SoPlex::EPSILON_UPDATE] = "epsilon_update";
365  description[SoPlex::EPSILON_UPDATE] = "zero tolerance used in update of the factorization";
366  lower[SoPlex::EPSILON_UPDATE] = 0.0;
367  upper[SoPlex::EPSILON_UPDATE] = 1.0;
369 
370  ///@todo define suitable values depending on Real type
371  // pivot zero tolerance used in factorization
372  name[SoPlex::EPSILON_PIVOT] = "epsilon_pivot";
373  description[SoPlex::EPSILON_PIVOT] = "pivot zero tolerance used in factorization";
374  lower[SoPlex::EPSILON_PIVOT] = 0.0;
375  upper[SoPlex::EPSILON_PIVOT] = 1.0;
377 
378  ///@todo define suitable values depending on Real type
379  // infinity threshold
380  name[SoPlex::INFTY] = "infty";
381  description[SoPlex::INFTY] = "infinity threshold";
382  lower[SoPlex::INFTY] = 1e10;
383  upper[SoPlex::INFTY] = 1e100;
385 
386  // time limit in seconds (INFTY if unlimited)
387  name[SoPlex::TIMELIMIT] = "timelimit";
388  description[SoPlex::TIMELIMIT] = "time limit in seconds";
389  lower[SoPlex::TIMELIMIT] = 0.0;
392 
393  // lower limit on objective value
394  name[SoPlex::OBJLIMIT_LOWER] = "objlimit_lower";
395  description[SoPlex::OBJLIMIT_LOWER] = "lower limit on objective value";
399 
400  // upper limit on objective value
401  name[SoPlex::OBJLIMIT_UPPER] = "objlimit_upper";
402  description[SoPlex::OBJLIMIT_UPPER] = "upper limit on objective value";
406 
407  // working tolerance for feasibility in floating-point solver during iterative refinement
408  name[SoPlex::FPFEASTOL] = "fpfeastol";
409  description[SoPlex::FPFEASTOL] = "working tolerance for feasibility in floating-point solver during iterative refinement";
410  lower[SoPlex::FPFEASTOL] = 1e-12;
411  upper[SoPlex::FPFEASTOL] = 1.0;
413 
414  // working tolerance for optimality in floating-point solver during iterative refinement
415  name[SoPlex::FPOPTTOL] = "fpopttol";
416  description[SoPlex::FPOPTTOL] = "working tolerance for optimality in floating-point solver during iterative refinement";
417  lower[SoPlex::FPOPTTOL] = 1e-12;
418  upper[SoPlex::FPOPTTOL] = 1.0;
420 
421  // maximum increase of scaling factors between refinements
422  name[SoPlex::MAXSCALEINCR] = "maxscaleincr";
423  description[SoPlex::MAXSCALEINCR] = "maximum increase of scaling factors between refinements";
424  lower[SoPlex::MAXSCALEINCR] = 1.0;
427 
428  // lower threshold in lifting (nonzero matrix coefficients with smaller absolute value will be reformulated)
429  name[SoPlex::LIFTMINVAL] = "liftminval";
430  description[SoPlex::LIFTMINVAL] = "lower threshold in lifting (nonzero matrix coefficients with smaller absolute value will be reformulated)";
431  lower[SoPlex::LIFTMINVAL] = 0.0;
432  upper[SoPlex::LIFTMINVAL] = 0.1;
433  defaultValue[SoPlex::LIFTMINVAL] = 0.000976562; // = 1/1024
434 
435  // upper threshold in lifting (nonzero matrix coefficients with larger absolute value will be reformulated)
436  name[SoPlex::LIFTMAXVAL] = "liftmaxval";
437  description[SoPlex::LIFTMAXVAL] = "lower threshold in lifting (nonzero matrix coefficients with smaller absolute value will be reformulated)";
438  lower[SoPlex::LIFTMAXVAL] = 10.0;
441 
442  // threshold for using sparse pricing (no. of violations need to be smaller than threshold * dimension of problem)
443  name[SoPlex::SPARSITY_THRESHOLD] = "sparsity_threshold";
444  description[SoPlex::SPARSITY_THRESHOLD] = "sparse pricing threshold (#violations < dimension * SPARSITY_THRESHOLD activates sparse pricing)";
445  lower[SoPlex::SPARSITY_THRESHOLD] = 0.0;
446  upper[SoPlex::SPARSITY_THRESHOLD] = 1.0;
448 
449  // threshold on number of rows vs. number of columns for switching from column to row representations in auto mode
450  name[SoPlex::REPRESENTATION_SWITCH] = "representation_switch";
451  description[SoPlex::REPRESENTATION_SWITCH] = "threshold on number of rows vs. number of columns for switching from column to row representations in auto mode";
452  lower[SoPlex::REPRESENTATION_SWITCH] = 0.0;
455 
456  // geometric frequency at which to apply rational reconstruction
457  name[SoPlex::RATREC_FREQ] = "ratrec_freq";
458  description[SoPlex::RATREC_FREQ] = "geometric frequency at which to apply rational reconstruction";
459  lower[SoPlex::RATREC_FREQ] = 1.0;
462 
463  // minimal reduction (sum of removed rows/cols) to continue simplification
464  name[SoPlex::MINRED] = "minred";
465  description[SoPlex::MINRED] = "minimal reduction (sum of removed rows/cols) to continue simplification";
466  lower[SoPlex::MINRED] = 0.0;
467  upper[SoPlex::MINRED] = 1.0;
469 
470  // refactor threshold for nonzeros in last factorized basis matrix compared to updated basis matrix
471  name[SoPlex::REFAC_BASIS_NNZ] = "refac_basis_nnz";
472  description[SoPlex::REFAC_BASIS_NNZ] = "refactor threshold for nonzeros in last factorized basis matrix compared to updated basis matrix";
473  lower[SoPlex::REFAC_BASIS_NNZ] = 1.0;
474  upper[SoPlex::REFAC_BASIS_NNZ] = 100.0;
476 
477  // refactor threshold for fill-in in current factor update compared to fill-in in last factorization
478  name[SoPlex::REFAC_UPDATE_FILL] = "refac_update_fill";
479  description[SoPlex::REFAC_UPDATE_FILL] = "refactor threshold for fill-in in current factor update compared to fill-in in last factorization";
480  lower[SoPlex::REFAC_UPDATE_FILL] = 1.0;
481  upper[SoPlex::REFAC_UPDATE_FILL] = 100.0;
483 
484  // refactor threshold for memory growth in factorization since last refactorization
485  name[SoPlex::REFAC_MEM_FACTOR] = "refac_mem_factor";
486  description[SoPlex::REFAC_MEM_FACTOR] = "refactor threshold for memory growth in factorization since last refactorization";
487  lower[SoPlex::REFAC_MEM_FACTOR] = 1.0;
488  upper[SoPlex::REFAC_MEM_FACTOR] = 10.0;
490 
491  // accuracy of conjugate gradient method in least squares scaling (higher value leads to more iterations)
492  name[SoPlex::LEASTSQ_ACRCY] = "leastsq_acrcy";
493  description[SoPlex::LEASTSQ_ACRCY] = "accuracy of conjugate gradient method in least squares scaling (higher value leads to more iterations)";
494  lower[SoPlex::LEASTSQ_ACRCY] = 1.0;
497 
498  // objective offset
499  name[SoPlex::OBJ_OFFSET] = "obj_offset";
500  description[SoPlex::OBJ_OFFSET] = "objective offset to be used";
504  }
505 
506 #ifdef SOPLEX_WITH_RATIONALPARAM
507  SoPlex::Settings::RationalParam::RationalParam() {}
508 #endif
509 
511  {
512  for( int i = 0; i < SoPlex::BOOLPARAM_COUNT; i++ )
514 
515  for( int i = 0; i < SoPlex::INTPARAM_COUNT; i++ )
517 
518  for( int i = 0; i < SoPlex::REALPARAM_COUNT; i++ )
520 
521 #ifdef SOPLEX_WITH_RATIONALPARAM
522  for( int i = 0; i < SoPlex::RATIONALPARAM_COUNT; i++ )
523  _rationalParamValues[i] = rationalParam.defaultValue[i];
524 #endif
525  }
526 
528  {
529  *this = settings;
530  }
531 
533  {
534  for( int i = 0; i < SoPlex::BOOLPARAM_COUNT; i++ )
535  _boolParamValues[i] = settings._boolParamValues[i];
536 
537  for( int i = 0; i < SoPlex::INTPARAM_COUNT; i++ )
538  _intParamValues[i] = settings._intParamValues[i];
539 
540  for( int i = 0; i < SoPlex::REALPARAM_COUNT; i++ )
541  _realParamValues[i] = settings._realParamValues[i];
542 
543 #ifdef SOPLEX_WITH_RATIONALPARAM
544  for( int i = 0; i < SoPlex::RATIONALPARAM_COUNT; i++ )
545  _rationalParamValues[i] = settings._rationalParamValues[i];
546 #endif
547 
548  return *this;
549  }
550 
554 #ifdef SOPLEX_WITH_RATIONALPARAM
555  SoPlex::Settings::RationalParam SoPlex::Settings::rationalParam;
556 #endif
557 
558  /// default constructor
560  : _statistics(0)
561  , _currentSettings(0)
562  , _scalerUniequi(false)
563  , _scalerBiequi(true)
564  , _scalerGeo1(false, 1)
565  , _scalerGeo8(false, 8)
566  , _scalerGeoequi(true)
567  , _scalerLeastsq()
568  , _simplifier(0)
569  , _scaler(0)
570  , _starter(0)
571  , _rationalLP(0)
573  , _status(SPxSolver::UNKNOWN)
574  , _hasBasis(false)
575  , _hasSolReal(false)
576  , _hasSolRational(false)
577  , _rationalPosone(1)
578  , _rationalNegone(-1)
579  , _rationalZero(0)
580  {
581  // transfer message handler
589 
590  // give lu factorization to solver
592 
593  // the real LP is initially stored in the solver; the rational LP is constructed, when the parameter SYNCMODE is
594  // initialized in setSettings() below
595  _realLP = &_solver;
596  _isRealLPLoaded = true;
597  _isRealLPScaled = false;
598  _applyPolishing = false;
599  _optimizeCalls = 0;
600  _unscaleCalls = 0;
603 
604  // initialize statistics
607 
608  // initialize parameter settings to default
612 
614 
615  assert(_isConsistent());
616  }
617 
618 
619 
620  /// assignment operator
622  {
623  if( this != &rhs )
624  {
625  // copy message handler
626  spxout = rhs.spxout;
627 
628  // copy statistics
629  *_statistics = *(rhs._statistics);
630 
631  // copy settings
633 
634  // copy solver components
635  _solver = rhs._solver;
636  _slufactor = rhs._slufactor;
640  _scalerGeo1 = rhs._scalerGeo1;
641  _scalerGeo8 = rhs._scalerGeo8;
645  _starterSum = rhs._starterSum;
647  _pricerAuto = rhs._pricerAuto;
657 
658  // copy solution data
659  _status = rhs._status;
663 
664  if( rhs._hasSolReal )
665  _solReal = rhs._solReal;
666 
667  if( rhs._hasSolRational )
669 
670  // set message handlers in members
678 
679  // transfer the lu solver
681 
682  // initialize pointers for simplifier, scaler, and starter
686 
687  // copy real LP if different from the LP in the solver
688  if( rhs._realLP != &(rhs._solver) )
689  {
690  _realLP = 0;
692  _realLP = new (_realLP) SPxLPReal(*(rhs._realLP));
693  }
694  else
695  _realLP = &_solver;
696 
697  // copy rational LP
698  if( rhs._rationalLP == 0 )
699  {
701  _rationalLP = 0;
702  }
703  else
704  {
706  _rationalLP = 0;
709  }
710 
711  // copy rational factorization
714 
715  // copy boolean flags
718  _hasSolReal = rhs._hasSolReal;
720  _hasBasis = rhs._hasBasis;
722 
723  // rational constants do not need to be assigned
724  _rationalPosone = 1;
725  _rationalNegone = -1;
726  _rationalZero = 0;
727  }
728 
729  assert(_isConsistent());
730 
731  return *this;
732  }
733 
734 
735 
736  /// copy constructor
737  ///@todo improve performance by implementing a separate copy constructor
738  SoPlex::SoPlex(const SoPlex& rhs)
739  {
740  // allocate memory as in default constructor
741  _statistics = 0;
744 
745  _currentSettings = 0;
748 
749  // call assignment operator
750  *this = rhs;
751  }
752 
753 
754 
755  /// destructor
757  {
758  assert(_isConsistent());
759 
760  // free settings
761  _currentSettings->~Settings();
763 
764  // free statistics
767 
768  // free real LP if different from the LP in the solver
769  assert(_realLP != 0);
770  if( _realLP != &_solver )
771  {
772  _realLP->~SPxLPReal();
773  spx_free(_realLP);
774  }
775 
776  // free rational LP
777  if( _rationalLP != 0 )
778  {
779  _rationalLP->~SPxLPRational();
781  }
782 
783  // free unit vectors
784  for( int i = 0; i < _unitMatrixRational.size(); i++ )
785  {
786  if( _unitMatrixRational[i] != 0 )
787  {
788  _unitMatrixRational[i]->~UnitVectorRational();
790  }
791  }
792  }
793 
794 
795 
796  /// returns number of rows
798  {
799  assert(_realLP != 0);
800  return _realLP->nRows();
801  }
802 
803 
804 
805  /// returns number of columns
807  {
808  assert(_realLP != 0);
809  return _realLP->nCols();
810  }
811 
812 
813 
814  /// returns number of nonzeros
816  {
817  assert(_realLP != 0);
818  return _realLP->nNzos();
819  }
820 
821 
822 
823  /// returns smallest non-zero element in absolute value
825  {
826  assert(_realLP != 0);
827  return _realLP->minAbsNzo();
828  }
829 
830 
831 
832  /// returns biggest non-zero element in absolute value
834  {
835  assert(_realLP != 0);
836  return _realLP->maxAbsNzo();
837  }
838 
839 
840 
841  /// returns (unscaled) coefficient
842  Real SoPlex::coefReal(int row, int col) const
843  {
844  if( _realLP->isScaled() )
845  {
846  assert(_scaler);
847  return _scaler->getCoefUnscaled(*_realLP, row, col);
848  }
849  else
850  return colVectorRealInternal(col)[row];
851  }
852 
853 
854 
855  /// returns vector of row \p i, ignoring scaling
857  {
858  assert(_realLP != 0);
859  return _realLP->rowVector(i);
860  }
861 
862 
863 
864  /// gets vector of row \p i
865  void SoPlex::getRowVectorReal(int i, DSVectorReal& row) const
866  {
867  assert(_realLP);
868 
869  if( _realLP->isScaled() )
870  {
871  assert(_scaler);
872  row.setMax(_realLP->rowVector(i).size());
873  _scaler->getRowUnscaled(*_realLP, i, row);
874  }
875  else
876  row = _realLP->rowVector(i);
877  }
878 
879 
880 
881  /// returns right-hand side vector, ignoring scaling
883  {
884  assert(_realLP != 0);
885  return _realLP->rhs();
886  }
887 
888 
889 
890  /// gets right-hand side vector
892  {
893  assert(_realLP);
894  _realLP->getRhsUnscaled(rhs);
895  }
896 
897 
898 
899  /// returns right-hand side of row \p i
900  Real SoPlex::rhsReal(int i) const
901  {
902  assert(_realLP != 0);
903  return _realLP->rhsUnscaled(i);
904  }
905 
906 
907 
908  /// returns left-hand side vector, ignoring scaling
910  {
911  assert(_realLP != 0);
912  return _realLP->lhs();
913  }
914 
915 
916 
917  /// gets left-hand side vector
919  {
920  assert(_realLP);
921  _realLP->getLhsUnscaled(lhs);
922  }
923 
924 
925 
926  /// returns left-hand side of row \p i
927  Real SoPlex::lhsReal(int i) const
928  {
929  assert(_realLP != 0);
930  return _realLP->lhsUnscaled(i);
931  }
932 
933 
934 
935  /// returns inequality type of row \p i
937  {
938  assert(_realLP != 0);
939  return _realLP->rowType(i);
940  }
941 
942 
943 
944  /// returns vector of col \p i, ignoring scaling
946  {
947  assert(_realLP != 0);
948  return _realLP->colVector(i);
949  }
950 
951 
952 
953  /// gets vector of col \p i
954  void SoPlex::getColVectorReal(int i, DSVectorReal& col) const
955  {
956  assert(_realLP);
957  _realLP->getColVectorUnscaled(i, col);
958  }
959 
960 
961 
962  /// returns upper bound vector
964  {
965  assert(_realLP != 0);
966  return _realLP->upper();
967  }
968 
969 
970 
971  /// returns upper bound of column \p i
972  Real SoPlex::upperReal(int i) const
973  {
974  assert(_realLP != 0);
975  return _realLP->upperUnscaled(i);
976  }
977 
978 
979 
980  /// gets upper bound vector
982  {
983  assert(_realLP != 0);
984  return _realLP->getUpperUnscaled(upper);
985  }
986 
987 
988 
989  /// returns lower bound vector
991  {
992  assert(_realLP != 0);
993  return _realLP->lower();
994  }
995 
996 
997 
998  /// returns lower bound of column \p i
999  Real SoPlex::lowerReal(int i) const
1000  {
1001  assert(_realLP != 0);
1002  return _realLP->lowerUnscaled(i);
1003  }
1004 
1005 
1006 
1007  /// gets lower bound vector
1009  {
1010  assert(_realLP != 0);
1011  return _realLP->getLowerUnscaled(lower);
1012  }
1013 
1014 
1015 
1016 
1017  /// gets objective function vector
1019  {
1020  assert(_realLP != 0);
1021  _realLP->getObjUnscaled(obj);
1022  }
1023 
1024 
1025 
1026  /// returns objective value of column \p i
1027  Real SoPlex::objReal(int i) const
1028  {
1029  assert(_realLP != 0);
1030  return _realLP->objUnscaled(i);
1031  }
1032 
1033 
1034 
1035  /// returns objective function vector after transformation to a maximization problem; since this is how it is stored
1036  /// internally, this is generally faster
1038  {
1039  assert(_realLP != 0);
1040  return _realLP->maxObj();
1041  }
1042 
1043 
1044 
1045  /// returns objective value of column \p i after transformation to a maximization problem; since this is how it is
1046  /// stored internally, this is generally faster
1048  {
1049  assert(_realLP != 0);
1050  return _realLP->maxObjUnscaled(i);
1051  }
1052 
1053 
1054 
1055  /// gets number of available dual norms
1056  void SoPlex::getNdualNorms(int& nnormsRow, int& nnormsCol) const
1057  {
1058  _solver.getNdualNorms(nnormsRow, nnormsCol);
1059  }
1060 
1061 
1062 
1063  /// gets steepest edge norms and returns false if they are not available
1064  bool SoPlex::getDualNorms(int& nnormsRow, int& nnormsCol, Real* norms) const
1065  {
1066  return _solver.getDualNorms(nnormsRow, nnormsCol, norms);
1067  }
1068 
1069 
1070 
1071  /// sets steepest edge norms and returns false if that's not possible
1072  bool SoPlex::setDualNorms(int nnormsRow, int nnormsCol, Real* norms)
1073  {
1074  return _solver.setDualNorms(nnormsRow, nnormsCol, norms);
1075  }
1076 
1077 
1078 
1079  /// pass integrality information about the variables to the solver
1080  void SoPlex::setIntegralityInformation( int ncols, int* intInfo)
1081  {
1082  assert(ncols == _solver.nCols() || (ncols == 0 && intInfo == NULL));
1083  _solver.setIntegralityInformation(ncols, intInfo);
1084  }
1085 
1086 
1087 
1088  /// returns number of rows
1090  {
1091  assert(_rationalLP != 0);
1092  return _rationalLP->nRows();
1093  }
1094 
1095 
1096 
1097  /// returns number of columns
1099  {
1100  assert(_rationalLP != 0);
1101  return _rationalLP->nCols();
1102  }
1103 
1104 
1105 
1106  /// returns number of nonzeros
1108  {
1109  assert(_rationalLP != 0);
1110  return _rationalLP->nNzos();
1111  }
1112 
1113 
1114 
1115  /// returns smallest non-zero element in absolute value
1117  {
1118  assert(_rationalLP != 0);
1119  return _rationalLP->minAbsNzo();
1120  }
1121 
1122 
1123 
1124  /// returns biggest non-zero element in absolute value
1126  {
1127  assert(_rationalLP != 0);
1128  return _rationalLP->maxAbsNzo();
1129  }
1130 
1131 
1132 
1133  /// gets row \p i
1134  void SoPlex::getRowRational(int i, LPRowRational& lprow) const
1135  {
1136  assert(_rationalLP != 0);
1137  _rationalLP->getRow(i, lprow);
1138  }
1139 
1140 
1141 
1142  /// gets rows \p start, ..., \p end.
1143  void SoPlex::getRowsRational(int start, int end, LPRowSetRational& lprowset) const
1144  {
1145  assert(_rationalLP != 0);
1146  _rationalLP->getRows(start, end, lprowset);
1147  }
1148 
1149 
1150 
1151  /// returns vector of row \p i
1153  {
1154  assert(_rationalLP != 0);
1155  return _rationalLP->rowVector(i);
1156  }
1157 
1158 
1159 
1160  /// returns right-hand side vector
1162  {
1163  assert(_rationalLP != 0);
1164  return _rationalLP->rhs();
1165  }
1166 
1167 
1168 
1169  /// returns right-hand side of row \p i
1170  const Rational& SoPlex::rhsRational(int i) const
1171  {
1172  assert(_rationalLP != 0);
1173  return _rationalLP->rhs(i);
1174  }
1175 
1176 
1177 
1178  /// returns left-hand side vector
1180  {
1181  assert(_rationalLP != 0);
1182  return _rationalLP->lhs();
1183  }
1184 
1185 
1186 
1187  /// returns left-hand side of row \p i
1188  const Rational& SoPlex::lhsRational(int i) const
1189  {
1190  assert(_rationalLP != 0);
1191  return _rationalLP->lhs(i);
1192  }
1193 
1194 
1195 
1196  /// returns inequality type of row \p i
1198  {
1199  assert(_rationalLP != 0);
1200  return _rationalLP->rowType(i);
1201  }
1202 
1203 
1204 
1205  /// gets column \p i
1206  void SoPlex::getColRational(int i, LPColRational& lpcol) const
1207  {
1208  assert(_rationalLP != 0);
1209  return _rationalLP->getCol(i, lpcol);
1210  }
1211 
1212 
1213 
1214  /// gets columns \p start, ..., \p end
1215  void SoPlex::getColsRational(int start, int end, LPColSetRational& lpcolset) const
1216  {
1217  assert(_rationalLP != 0);
1218  return _rationalLP->getCols(start, end, lpcolset);
1219  }
1220 
1221 
1222 
1223  /// returns vector of column \p i
1225  {
1226  assert(_rationalLP != 0);
1227  return _rationalLP->colVector(i);
1228  }
1229 
1230 
1231 
1232  /// returns upper bound vector
1234  {
1235  assert(_rationalLP != 0);
1236  return _rationalLP->upper();
1237  }
1238 
1239 
1240 
1241  /// returns upper bound of column \p i
1242  const Rational& SoPlex::upperRational(int i) const
1243  {
1244  assert(_rationalLP != 0);
1245  return _rationalLP->upper(i);
1246  }
1247 
1248 
1249 
1250  /// returns lower bound vector
1252  {
1253  assert(_rationalLP != 0);
1254  return _rationalLP->lower();
1255  }
1256 
1257 
1258 
1259  /// returns lower bound of column \p i
1260  const Rational& SoPlex::lowerRational(int i) const
1261  {
1262  assert(_rationalLP != 0);
1263  return _rationalLP->lower(i);
1264  }
1265 
1266 
1267 
1268  /// gets objective function vector
1270  {
1271  assert(_rationalLP != 0);
1272  _rationalLP->getObj(obj);
1273  }
1274 
1275 
1276 
1277  /// gets objective value of column \p i
1278  void SoPlex::getObjRational(int i, Rational& obj) const
1279  {
1280  obj = maxObjRational(i);
1282  obj *= -1;
1283  }
1284 
1285 
1286 
1287  /// returns objective value of column \p i
1289  {
1290  assert(_rationalLP != 0);
1291  return _rationalLP->obj(i);
1292  }
1293 
1294 
1295 
1296  /// returns objective function vector after transformation to a maximization problem; since this is how it is stored
1297  /// internally, this is generally faster
1299  {
1300  assert(_rationalLP != 0);
1301  return _rationalLP->maxObj();
1302  }
1303 
1304 
1305 
1306  /// returns objective value of column \p i after transformation to a maximization problem; since this is how it is
1307  /// stored internally, this is generally faster
1308  const Rational& SoPlex::maxObjRational(int i) const
1309  {
1310  assert(_rationalLP != 0);
1311  return _rationalLP->maxObj(i);
1312  }
1313 
1314 
1315 
1316  /// adds a single row
1317  void SoPlex::addRowReal(const LPRowReal& lprow)
1318  {
1319  assert(_realLP != 0);
1320 
1321  _addRowReal(lprow);
1322 
1324  {
1325  _rationalLP->addRow(lprow);
1327  }
1328 
1330  }
1331 
1332 
1333 
1334  /// adds multiple rows
1335  void SoPlex::addRowsReal(const LPRowSetReal& lprowset)
1336  {
1337  assert(_realLP != 0);
1338 
1339  _addRowsReal(lprowset);
1340 
1342  {
1343  _rationalLP->addRows(lprowset);
1345  }
1346 
1348  }
1349 
1350 
1351 
1352  /// adds a single column
1353  void SoPlex::addColReal(const LPColReal& lpcol)
1354  {
1355  assert(_realLP != 0);
1356 
1357  _addColReal(lpcol);
1358 
1360  {
1361  _rationalLP->addCol(lpcol);
1363  }
1364 
1366  }
1367 
1368 
1369 
1370  /// adds multiple columns
1371  void SoPlex::addColsReal(const LPColSetReal& lpcolset)
1372  {
1373  assert(_realLP != 0);
1374 
1375  _addColsReal(lpcolset);
1376 
1378  {
1379  _rationalLP->addCols(lpcolset);
1381  }
1382 
1384  }
1385 
1386 
1387 
1388  /// replaces row \p i with \p lprow
1389  void SoPlex::changeRowReal(int i, const LPRowReal& lprow)
1390  {
1391  assert(_realLP != 0);
1392 
1393  _changeRowReal(i, lprow);
1394 
1396  {
1397  _rationalLP->changeRow(i, lprow);
1398  _rowTypes[i] = _rangeTypeReal(lprow.lhs(), lprow.rhs());
1400  }
1401 
1403  }
1404 
1405 
1406 
1407  /// changes left-hand side vector for constraints to \p lhs
1409  {
1410  assert(_realLP != 0);
1411 
1412  _changeLhsReal(lhs);
1413 
1415  {
1417  for( int i = 0; i < numRowsRational(); i++ )
1419  }
1420 
1422  }
1423 
1424 
1425 
1426  /// changes left-hand side of row \p i to \p lhs
1427  void SoPlex::changeLhsReal(int i, const Real& lhs)
1428  {
1429  assert(_realLP != 0);
1430 
1431  _changeLhsReal(i, lhs);
1432 
1434  {
1435  _rationalLP->changeLhs(i, lhs);
1437  }
1438 
1440  }
1441 
1442 
1443 
1444  /// changes right-hand side vector to \p rhs
1446  {
1447  assert(_realLP != 0);
1448 
1449  _changeRhsReal(rhs);
1450 
1452  {
1454  for( int i = 0; i < numRowsRational(); i++ )
1456  }
1457 
1459  }
1460 
1461 
1462 
1463  /// changes right-hand side of row \p i to \p rhs
1464  void SoPlex::changeRhsReal(int i, const Real& rhs)
1465  {
1466  assert(_realLP != 0);
1467 
1468  _changeRhsReal(i, rhs);
1469 
1471  {
1472  _rationalLP->changeRhs(i, rhs);
1474  }
1475 
1477  }
1478 
1479 
1480 
1481  /// changes left- and right-hand side vectors
1482  void SoPlex::changeRangeReal(const VectorReal& lhs, const VectorReal& rhs)
1483  {
1484  assert(_realLP != 0);
1485 
1486  _changeRangeReal(lhs, rhs);
1487 
1489  {
1491  for( int i = 0; i < numRowsRational(); i++ )
1492  _rowTypes[i] = _rangeTypeReal(lhs[i], rhs[i]);
1493  }
1494 
1496  }
1497 
1498 
1499 
1500  /// changes left- and right-hand side of row \p i
1501  void SoPlex::changeRangeReal(int i, const Real& lhs, const Real& rhs)
1502  {
1503  assert(_realLP != 0);
1504 
1505  _changeRangeReal(i,lhs, rhs);
1506 
1508  {
1509  _rationalLP->changeRange(i, lhs, rhs);
1510  _rowTypes[i] = _rangeTypeReal(lhs, rhs);
1511  }
1512 
1514  }
1515 
1516 
1517 
1518  /// replaces column \p i with \p lpcol
1519  void SoPlex::changeColReal(int i, const LPColReal& lpcol)
1520  {
1521  assert(_realLP != 0);
1522 
1523  _changeColReal(i, lpcol);
1524 
1526  {
1527  _rationalLP->changeCol(i, lpcol);
1528  _colTypes[i] = _rangeTypeReal(lpcol.lower(), lpcol.upper());
1530  }
1531 
1533  }
1534 
1535 
1536 
1537  /// changes vector of lower bounds to \p lower
1539  {
1540  assert(_realLP != 0);
1541 
1542  _changeLowerReal(lower);
1543 
1545  {
1547  for( int i = 0; i < numColsRational(); i++ )
1549  }
1550 
1551 
1553  }
1554 
1555 
1556 
1557  /// changes lower bound of column i to \p lower
1558  void SoPlex::changeLowerReal(int i, const Real& lower)
1559  {
1560  assert(_realLP != 0);
1561 
1562  _changeLowerReal(i, lower);
1563 
1565  {
1566  _rationalLP->changeLower(i, lower);
1568  }
1569 
1571  }
1572 
1573 
1574 
1575  /// changes vector of upper bounds to \p upper
1577  {
1578  assert(_realLP != 0);
1579 
1580  _changeUpperReal(upper);
1581 
1583  {
1585  for( int i = 0; i < numColsRational(); i++ )
1587  }
1588 
1590  }
1591 
1592 
1593 
1594  /// changes \p i 'th upper bound to \p upper
1595  void SoPlex::changeUpperReal(int i, const Real& upper)
1596  {
1597  assert(_realLP != 0);
1598 
1599  _changeUpperReal(i, upper);
1600 
1602  {
1603  _rationalLP->changeUpper(i, upper);
1605  }
1606 
1608  }
1609 
1610 
1611 
1612  /// changes vectors of column bounds to \p lower and \p upper
1613  void SoPlex::changeBoundsReal(const VectorReal& lower, const VectorReal& upper)
1614  {
1615  assert(_realLP != 0);
1616 
1617  _changeBoundsReal(lower, upper);
1618 
1620  {
1622  for( int i = 0; i < numColsRational(); i++ )
1623  _colTypes[i] = _rangeTypeReal(lower[i], upper[i]);
1624  }
1625 
1627  }
1628 
1629 
1630 
1631  /// changes bounds of column \p i to \p lower and \p upper
1632  void SoPlex::changeBoundsReal(int i, const Real& lower, const Real& upper)
1633  {
1634  assert(_realLP != 0);
1635 
1636  _changeBoundsReal(i, lower, upper);
1637 
1639  {
1640  _rationalLP->changeBounds(i, lower, upper);
1641  _colTypes[i] = _rangeTypeReal(lower, upper);
1642  }
1644  }
1645 
1646 
1647 
1648  /// changes objective function vector to \p obj
1650  {
1651  assert(_realLP != 0);
1652 
1653  bool scale = _realLP->isScaled();
1654  _realLP->changeObj(obj, scale);
1655 
1658 
1660  }
1661 
1662 
1663 
1664  /// changes objective coefficient of column i to \p obj
1665  void SoPlex::changeObjReal(int i, const Real& obj)
1666  {
1667  assert(_realLP != 0);
1668 
1669  bool scale = _realLP->isScaled();
1670  _realLP->changeObj(i, obj, scale);
1671 
1673  _rationalLP->changeObj(i, obj);
1674 
1676  }
1677 
1678 
1679 
1680  /// changes matrix entry in row \p i and column \p j to \p val
1681  void SoPlex::changeElementReal(int i, int j, const Real& val)
1682  {
1683  assert(_realLP != 0);
1684 
1685  _changeElementReal(i, j, val);
1686 
1688  _rationalLP->changeElement(i, j, val);
1689 
1691  }
1692 
1693 
1694 
1695  /// removes row \p i
1697  {
1698  assert(_realLP != 0);
1699 
1700  _removeRowReal(i);
1701 
1703  {
1704  _rationalLP->removeRow(i);
1705  // only swap elements if not the last one was removed
1706  if( i < _rationalLP->nRows() )
1707  {
1709  assert(_rowTypes[i] == _rangeTypeRational(lhsRational(i), rhsRational(i)));
1710  }
1712  }
1713 
1715  }
1716 
1717 
1718 
1719  /// removes all rows with an index \p i such that \p perm[i] < 0; upon completion, \p perm[i] >= 0 indicates the
1720  /// new index where row \p i has been moved to; note that \p perm must point to an array of size at least
1721  /// #numRowsReal()
1722  void SoPlex::removeRowsReal(int perm[])
1723  {
1724  assert(_realLP != 0);
1725 
1726  const int oldsize = numRowsReal();
1727  _removeRowsReal(perm);
1728 
1730  {
1731  _rationalLP->removeRows(perm);
1732  for( int i = 0; i < oldsize; i++ )
1733  {
1734  if( perm[i] >= 0 )
1735  _rowTypes[perm[i]] = _rowTypes[i];
1736  }
1738  for( int i = 0; i < numRowsRational(); i++ )
1739  {
1740  assert(_rowTypes[i] == _rangeTypeRational(lhsRational(i), rhsRational(i)));
1741  }
1742  }
1743 
1745  }
1746 
1747 
1748 
1749  /// remove all rows with indices in array \p idx of size \p n; an array \p perm of size #numRowsReal() may be passed
1750  /// as buffer memory
1751  void SoPlex::removeRowsReal(int idx[], int n, int perm[])
1752  {
1753  if( perm == 0 )
1754  {
1756  _idxToPerm(idx, n, p.get_ptr(), numRowsReal());
1758  }
1759  else
1760  {
1761  _idxToPerm(idx, n, perm, numRowsReal());
1762  SoPlex::removeRowsReal(perm);
1763  }
1764  }
1765 
1766 
1767 
1768  /// removes rows \p start to \p end including both; an array \p perm of size #numRowsReal() may be passed as buffer
1769  /// memory
1770  void SoPlex::removeRowRangeReal(int start, int end, int perm[])
1771  {
1772  if( perm == 0 )
1773  {
1775  _rangeToPerm(start, end, p.get_ptr(), numRowsReal());
1777  }
1778  else
1779  {
1780  _rangeToPerm(start, end, perm, numRowsReal());
1781  SoPlex::removeRowsReal(perm);
1782  }
1783  }
1784 
1785 
1786 
1787  /// removes column i
1789  {
1790  assert(_realLP != 0);
1791 
1792  _removeColReal(i);
1793 
1795  {
1796  _rationalLP->removeCol(i);
1797  // only swap elements if not the last one was removed
1798  if( i < _rationalLP->nCols() )
1799  {
1802  }
1804  }
1805 
1807  }
1808 
1809 
1810 
1811  /// removes all columns with an index \p i such that \p perm[i] < 0; upon completion, \p perm[i] >= 0 indicates the
1812  /// new index where column \p i has been moved to; note that \p perm must point to an array of size at least
1813  /// #numColsReal()
1814  void SoPlex::removeColsReal(int perm[])
1815  {
1816  assert(_realLP != 0);
1817 
1818  const int oldsize = numColsReal();
1819  _removeColsReal(perm);
1820 
1822  {
1823  _rationalLP->removeCols(perm);
1824  for( int i = 0; i < oldsize; i++ )
1825  {
1826  if( perm[i] >= 0 )
1827  _colTypes[perm[i]] = _colTypes[i];
1828  }
1830  for( int i = 0; i < numColsRational(); i++ )
1831  {
1833  }
1834  }
1835 
1837  }
1838 
1839 
1840 
1841  /// remove all columns with indices in array \p idx of size \p n; an array \p perm of size #numColsReal() may be
1842  /// passed as buffer memory
1843  void SoPlex::removeColsReal(int idx[], int n, int perm[])
1844  {
1845  if( perm == 0 )
1846  {
1848  _idxToPerm(idx, n, p.get_ptr(), numColsReal());
1850  }
1851  else
1852  {
1853  _idxToPerm(idx, n, perm, numColsReal());
1854  SoPlex::removeColsReal(perm);
1855  }
1856  }
1857 
1858 
1859 
1860  /// removes columns \p start to \p end including both; an array \p perm of size #numColsReal() may be passed as
1861  /// buffer memory
1862  void SoPlex::removeColRangeReal(int start, int end, int perm[])
1863  {
1864  if( perm == 0 )
1865  {
1867  _rangeToPerm(start, end, p.get_ptr(), numColsReal());
1869  }
1870  else
1871  {
1872  _rangeToPerm(start, end, perm, numColsReal());
1873  SoPlex::removeColsReal(perm);
1874  }
1875  }
1876 
1877 
1878 
1879  /// clears the LP
1881  {
1882  assert(_realLP != 0);
1883 
1884  _realLP->clear();
1885  _hasBasis = false;
1887 
1889  {
1890  _rationalLP->clear();
1891  _rowTypes.clear();
1892  _colTypes.clear();
1893  }
1894 
1896  }
1897 
1898 
1899 
1900  /// synchronizes real LP with rational LP, i.e., copies (rounded) rational LP into real LP, if sync mode is manual
1902  {
1903  assert(_isConsistent());
1904 
1906  _syncLPReal();
1907  }
1908 
1909 
1910 
1911  /// adds a single row
1913  {
1914  assert(_rationalLP != 0);
1915 
1917  return;
1918 
1919  _rationalLP->addRow(lprow);
1921 
1923  _addRowReal(lprow);
1924 
1926  }
1927 
1928 
1929 
1930 #ifdef SOPLEX_WITH_GMP
1931  /// adds a single row
1932  void SoPlex::addRowRational(const mpq_t* lhs, const mpq_t* rowValues, const int* rowIndices, const int rowSize, const mpq_t* rhs)
1933  {
1934  assert(_rationalLP != 0);
1935 
1937  return;
1938 
1939  _rationalLP->addRow(lhs, rowValues, rowIndices, rowSize, rhs);
1941 
1942  int i = numRowsRational() - 1;
1945 
1947  }
1948 
1949 
1950 
1951  /// adds a set of rows
1952  void SoPlex::addRowsRational(const mpq_t* lhs, const mpq_t* rowValues, const int* rowIndices, const int* rowStarts, const int* rowLengths, const int numRows, const int numValues, const mpq_t* rhs)
1953  {
1954  assert(_rationalLP != 0);
1955 
1957  return;
1958 
1959  _rationalLP->addRows(lhs, rowValues, rowIndices, rowStarts, rowLengths, numRows, numValues, rhs);
1961 
1963  {
1964  LPRowSetReal lprowset;
1965  for( int i = numRowsRational() - numRows; i < numRowsRational(); i++ )
1967  _addRowsReal(lprowset);
1968  }
1969 
1971  }
1972 #endif
1973 
1974 
1975 
1976  /// adds multiple rows
1978  {
1979  assert(_rationalLP != 0);
1980 
1982  return;
1983 
1984  _rationalLP->addRows(lprowset);
1986 
1988  _addRowsReal(lprowset);
1989 
1991  }
1992 
1993 
1994 
1995  /// adds a single column
1997  {
1998  assert(_rationalLP != 0);
1999 
2001  return;
2002 
2003  _rationalLP->addCol(lpcol);
2005 
2007  _addColReal(lpcol);
2008 
2010  }
2011 
2012 
2013 
2014 #ifdef SOPLEX_WITH_GMP
2015  /// adds a single column
2016  void SoPlex::addColRational(const mpq_t* obj, const mpq_t* lower, const mpq_t* colValues, const int* colIndices, const int colSize, const mpq_t* upper)
2017  {
2018  assert(_rationalLP != 0);
2019 
2021  return;
2022 
2023  _rationalLP->addCol(obj, lower, colValues, colIndices, colSize, upper);
2024  int i = numColsRational() - 1;
2026 
2030 
2032  }
2033 
2034 
2035 
2036  /// adds a set of columns
2037  void SoPlex::addColsRational(const mpq_t* obj, const mpq_t* lower, const mpq_t* colValues, const int* colIndices, const int* colStarts, const int* colLengths, const int numCols, const int numValues, const mpq_t* upper)
2038  {
2039  assert(_rationalLP != 0);
2040 
2042  return;
2043 
2044  _rationalLP->addCols(obj, lower, colValues, colIndices, colStarts, colLengths, numCols, numValues, upper);
2046 
2048  {
2049  LPColSetReal lpcolset;
2050  for( int i = numColsRational() - numCols; i < numColsRational(); i++ )
2051  lpcolset.add(Real(maxObjRational(i)) * (intParam(SoPlex::OBJSENSE) == SoPlex::OBJSENSE_MAXIMIZE ? 1.0 : -1.0),
2053  _addColsReal(lpcolset);
2054  }
2055 
2057  }
2058 #endif
2059 
2060 
2061 
2062  /// adds multiple columns
2064  {
2065  assert(_rationalLP != 0);
2066 
2068  return;
2069 
2070  _rationalLP->addCols(lpcolset);
2072 
2074  _addColsReal(lpcolset);
2075 
2077  }
2078 
2079 
2080 
2081  /// replaces row \p i with \p lprow
2082  void SoPlex::changeRowRational(int i, const LPRowRational& lprow)
2083  {
2084  assert(_rationalLP != 0);
2085 
2087  return;
2088 
2089  _rationalLP->changeRow(i, lprow);
2090  _rowTypes[i] = _rangeTypeRational(lprow.lhs(), lprow.rhs());
2092 
2094  _changeRowReal(i, lprow);
2095 
2097  }
2098 
2099 
2100 
2101  /// changes left-hand side vector for constraints to \p lhs
2103  {
2104  assert(_rationalLP != 0);
2105 
2107  return;
2108 
2109  _rationalLP->changeLhs(lhs);
2110  for( int i = 0; i < numRowsRational(); i++ )
2111  _rowTypes[i] = _rangeTypeRational(lhs[i], _rationalLP->rhs(i));
2112 
2115 
2117  }
2118 
2119 
2120 
2121  /// changes left-hand side of row \p i to \p lhs
2122  void SoPlex::changeLhsRational(int i, const Rational& lhs)
2123  {
2124  assert(_rationalLP != 0);
2125 
2127  return;
2128 
2129  _rationalLP->changeLhs(i, lhs);
2131 
2133  _changeLhsReal(i, Real(lhs));
2134 
2136  }
2137 
2138 
2139 
2140 #ifdef SOPLEX_WITH_GMP
2141  /// changes left-hand side of row \p i to \p lhs
2142  void SoPlex::changeLhsRational(int i, const mpq_t* lhs)
2143  {
2144  assert(_rationalLP != 0);
2145 
2147  return;
2148 
2149  _rationalLP->changeLhs(i, lhs);
2151 
2154 
2156  }
2157 #endif
2158 
2159 
2160 
2161  /// changes right-hand side vector to \p rhs
2163  {
2164  assert(_rationalLP != 0);
2165 
2167  return;
2168 
2169  _rationalLP->changeRhs(rhs);
2170  for( int i = 0; i < numRowsRational(); i++ )
2171  _rowTypes[i] = _rangeTypeRational(_rationalLP->lhs(i), rhs[i]);
2172 
2175 
2177  }
2178 
2179 
2180 
2181 #ifdef SOPLEX_WITH_GMP
2182  /// changes right-hand side vector to \p rhs
2183  void SoPlex::changeRhsRational(const mpq_t* rhs, int rhsSize)
2184  {
2185  assert(_rationalLP != 0);
2186 
2188  return;
2189 
2190  for( int i = 0; i < rhsSize; i++ )
2191  {
2192  _rationalLP->changeRhs(i, rhs[i]);
2194  }
2195 
2198 
2200  }
2201 #endif
2202 
2203 
2204 
2205  /// changes right-hand side of row \p i to \p rhs
2206  void SoPlex::changeRhsRational(int i, const Rational& rhs)
2207  {
2208  assert(_rationalLP != 0);
2209 
2211  return;
2212 
2213  _rationalLP->changeRhs(i, rhs);
2215 
2217  _changeRhsReal(i, Real(rhs));
2218 
2220  }
2221 
2222 
2223 
2224  /// changes left- and right-hand side vectors
2226  {
2227  assert(_rationalLP != 0);
2228 
2230  return;
2231 
2232  _rationalLP->changeRange(lhs, rhs);
2233  for( int i = 0; i < numRowsRational(); i++ )
2234  _rowTypes[i] = _rangeTypeRational(lhs[i], rhs[i]);
2235 
2238 
2240  }
2241 
2242 
2243 
2244  /// changes left- and right-hand side of row \p i
2245  void SoPlex::changeRangeRational(int i, const Rational& lhs, const Rational& rhs)
2246  {
2247  assert(_rationalLP != 0);
2248 
2250  return;
2251 
2252  _rationalLP->changeRange(i, lhs, rhs);
2253  _rowTypes[i] = _rangeTypeRational(lhs, rhs);
2254 
2256  _changeRangeReal(i, Real(lhs), Real(rhs));
2257 
2259  }
2260 
2261 
2262 
2263 #ifdef SOPLEX_WITH_GMP
2264  /// changes left-hand side of row \p i to \p lhs
2265  void SoPlex::changeRangeRational(int i, const mpq_t* lhs, const mpq_t* rhs)
2266  {
2267  assert(_rationalLP != 0);
2268 
2270  return;
2271 
2272  _rationalLP->changeRange(i, lhs, rhs);
2274 
2277 
2279  }
2280 #endif
2281 
2282 
2283 
2284  /// replaces column \p i with \p lpcol
2285  void SoPlex::changeColRational(int i, const LPColRational& lpcol)
2286  {
2287  assert(_rationalLP != 0);
2288 
2290  return;
2291 
2292  _rationalLP->changeCol(i, lpcol);
2293  _colTypes[i] = _rangeTypeRational(lpcol.lower(), lpcol.upper());
2295 
2297  _changeColReal(i, lpcol);
2298 
2300  }
2301 
2302 
2303 
2304  /// changes vector of lower bounds to \p lower
2306  {
2307  assert(_rationalLP != 0);
2308 
2310  return;
2311 
2312  _rationalLP->changeLower(lower);
2313  for( int i = 0; i < numColsRational(); i++ )
2314  _colTypes[i] = _rangeTypeRational(lower[i], _rationalLP->upper(i));
2315 
2317  _changeLowerReal(DVectorReal(lower));
2318 
2320  }
2321 
2322 
2323 
2324  /// changes lower bound of column i to \p lower
2325  void SoPlex::changeLowerRational(int i, const Rational& lower)
2326  {
2327  assert(_rationalLP != 0);
2328 
2330  return;
2331 
2332  _rationalLP->changeLower(i, lower);
2333  _colTypes[i] = _rangeTypeRational(lower, _rationalLP->upper(i));
2334 
2336  _changeLowerReal(i, Real(lower));
2337 
2339  }
2340 
2341 
2342 
2343 #ifdef SOPLEX_WITH_GMP
2344  /// changes lower bound of column i to \p lower
2345  void SoPlex::changeLowerRational(int i, const mpq_t* lower)
2346  {
2347  assert(_rationalLP != 0);
2348 
2350  return;
2351 
2352  _rationalLP->changeLower(i, lower);
2354 
2357 
2359  }
2360 #endif
2361 
2362 
2363 
2364  /// changes vector of upper bounds to \p upper
2366  {
2367  assert(_rationalLP != 0);
2368 
2370  return;
2371 
2372  _rationalLP->changeUpper(upper);
2373  for( int i = 0; i < numColsRational(); i++ )
2374  _colTypes[i] = _rangeTypeRational(_rationalLP->lower(i), upper[i]);
2375 
2377  _changeUpperReal(DVectorReal(upper));
2378 
2380  }
2381 
2382 
2383 
2384  /// changes \p i 'th upper bound to \p upper
2385  void SoPlex::changeUpperRational(int i, const Rational& upper)
2386  {
2387  assert(_rationalLP != 0);
2388 
2390  return;
2391 
2392  _rationalLP->changeUpper(i, upper);
2393  _colTypes[i] = _rangeTypeRational(_rationalLP->lower(i), upper);
2394 
2396  _changeUpperReal(i, Real(upper));
2397 
2399  }
2400 
2401 
2402 
2403 #ifdef SOPLEX_WITH_GMP
2404  /// changes upper bound of column i to \p upper
2405  void SoPlex::changeUpperRational(int i, const mpq_t* upper)
2406  {
2407  assert(_rationalLP != 0);
2408 
2410  return;
2411 
2412  _rationalLP->changeUpper(i, upper);
2414 
2417 
2419  }
2420 #endif
2421 
2422 
2423 
2424  /// changes vectors of column bounds to \p lower and \p upper
2426  {
2427  assert(_rationalLP != 0);
2428 
2430  return;
2431 
2432  _rationalLP->changeBounds(lower, upper);
2433  for( int i = 0; i < numColsRational(); i++ )
2434  _colTypes[i] = _rangeTypeRational(lower[i], upper[i]);
2435 
2437  _changeBoundsReal(DVectorReal(lower), DVectorReal(upper));
2438 
2440  }
2441 
2442 
2443 
2444  /// changes bounds of column \p i to \p lower and \p upper
2445  void SoPlex::changeBoundsRational(int i, const Rational& lower, const Rational& upper)
2446  {
2447  assert(_rationalLP != 0);
2448 
2450  return;
2451 
2452  _rationalLP->changeBounds(i, lower, upper);
2453  _colTypes[i] = _rangeTypeRational(lower, upper);
2454 
2456  _changeBoundsReal(i, Real(lower), Real(upper));
2457 
2459  }
2460 
2461 
2462 
2463 #ifdef SOPLEX_WITH_GMP
2464  /// changes bounds of column \p i to \p lower and \p upper
2465  void SoPlex::changeBoundsRational(int i, const mpq_t* lower, const mpq_t* upper)
2466  {
2467  assert(_rationalLP != 0);
2468 
2470  return;
2471 
2472  _rationalLP->changeBounds(i, lower, upper);
2474 
2477 
2479  }
2480 #endif
2481 
2482 
2483 
2484  /// changes objective function vector to \p obj
2486  {
2487  assert(_rationalLP != 0);
2488 
2490  return;
2491 
2492  _rationalLP->changeObj(obj);
2493 
2495  _realLP->changeObj(DVectorReal(obj));
2496 
2498  }
2499 
2500 
2501 
2502  /// changes objective coefficient of column i to \p obj
2503  void SoPlex::changeObjRational(int i, const Rational& obj)
2504  {
2505  assert(_rationalLP != 0);
2506 
2508  return;
2509 
2510  _rationalLP->changeObj(i, obj);
2511 
2513  _realLP->changeObj(i, Real(obj));
2514 
2516  }
2517 
2518 
2519 
2520 #ifdef SOPLEX_WITH_GMP
2521  /// changes objective coefficient of column i to \p obj
2522  void SoPlex::changeObjRational(int i, const mpq_t* obj)
2523  {
2524  assert(_rationalLP != 0);
2525 
2527  return;
2528 
2529  _rationalLP->changeObj(i, obj);
2530 
2532  _realLP->changeObj(i, Real(objRational(i)));
2533 
2535  }
2536 #endif
2537 
2538 
2539 
2540  /// changes matrix entry in row \p i and column \p j to \p val
2541  void SoPlex::changeElementRational(int i, int j, const Rational& val)
2542  {
2543  assert(_rationalLP != 0);
2544 
2546  return;
2547 
2548  _rationalLP->changeElement(i, j, val);
2549 
2551  _changeElementReal(i, j, Real(val));
2552 
2554  }
2555 
2556 
2557 #ifdef SOPLEX_WITH_GMP
2558  /// changes matrix entry in row \p i and column \p j to \p val
2559  void SoPlex::changeElementRational(int i, int j, const mpq_t* val)
2560  {
2561  assert(_rationalLP != 0);
2562 
2564  return;
2565 
2566  _rationalLP->changeElement(i, j, val);
2567 
2569  _changeElementReal(i, j, mpq_get_d(*val));
2570 
2572  }
2573 #endif
2574 
2575 
2576  /// removes row \p i
2578  {
2579  assert(_rationalLP != 0);
2580 
2582  return;
2583 
2584  _rationalLP->removeRow(i);
2585  // only swap elements if not the last one was removed
2586  if( i < _rationalLP->nRows() )
2587  {
2589  assert(_rowTypes[i] == _rangeTypeRational(lhsRational(i), rhsRational(i)));
2590  }
2592 
2594  _removeRowReal(i);
2595 
2597  }
2598 
2599 
2600 
2601  /// removes all rows with an index \p i such that \p perm[i] < 0; upon completion, \p perm[i] >= 0 indicates the new
2602  /// index where row \p i has been moved to; note that \p perm must point to an array of size at least
2603  /// #numRowsRational()
2605  {
2606  assert(_rationalLP != 0);
2607 
2609  return;
2610 
2611  const int oldsize = numRowsRational();
2612  _rationalLP->removeRows(perm);
2613  for( int i = 0; i < oldsize; i++ )
2614  {
2615  if( perm[i] >= 0 )
2616  _rowTypes[perm[i]] = _rowTypes[i];
2617  }
2619  for( int i = 0; i < numRowsRational(); i++ )
2620  {
2621  assert(_rowTypes[i] == _rangeTypeRational(lhsRational(i), rhsRational(i)));
2622  }
2623 
2624 
2626  _removeRowsReal(perm);
2627 
2629  }
2630 
2631 
2632 
2633  /// remove all rows with indices in array \p idx of size \p n; an array \p perm of size #numRowsRational() may be
2634  /// passed as buffer memory
2635  void SoPlex::removeRowsRational(int idx[], int n, int perm[])
2636  {
2637  if( perm == 0 )
2638  {
2640  _idxToPerm(idx, n, p.get_ptr(), numRowsRational());
2642  }
2643  else
2644  {
2645  _idxToPerm(idx, n, perm, numRowsRational());
2647  }
2648  }
2649 
2650 
2651 
2652  /// removes rows \p start to \p end including both; an array \p perm of size #numRowsRational() may be passed as
2653  /// buffer memory
2654  void SoPlex::removeRowRangeRational(int start, int end, int perm[])
2655  {
2656  if( perm == 0 )
2657  {
2659  _rangeToPerm(start, end, p.get_ptr(), numRowsRational());
2661  }
2662  else
2663  {
2664  _rangeToPerm(start, end, perm, numRowsRational());
2666  }
2667  }
2668 
2669 
2670 
2671  /// removes column i
2673  {
2674  assert(_rationalLP != 0);
2675 
2677  return;
2678 
2679  _rationalLP->removeCol(i);
2680  // only swap elements if not the last one was removed
2681  if( i < _rationalLP->nCols() )
2682  {
2685  }
2687 
2689  _removeColReal(i);
2690 
2692  }
2693 
2694 
2695 
2696  /// removes all columns with an index \p i such that \p perm[i] < 0; upon completion, \p perm[i] >= 0 indicates the
2697  /// new index where column \p i has been moved to; note that \p perm must point to an array of size at least
2698  /// #numColsRational()
2700  {
2701  assert(_rationalLP != 0);
2702 
2704  return;
2705 
2706  const int oldsize = numColsRational();
2707  _rationalLP->removeCols(perm);
2708  for( int i = 0; i < oldsize; i++ )
2709  {
2710  if( perm[i] >= 0 )
2711  _colTypes[perm[i]] = _colTypes[i];
2712  }
2714  for( int i = 0; i < numColsRational(); i++ )
2715  {
2717  }
2718 
2720  _removeColsReal(perm);
2721 
2723  }
2724 
2725 
2726 
2727  /// remove all columns with indices in array \p idx of size \p n; an array \p perm of size #numColsRational() may be
2728  /// passed as buffer memory
2729  void SoPlex::removeColsRational(int idx[], int n, int perm[])
2730  {
2731  if( perm == 0 )
2732  {
2734  _idxToPerm(idx, n, p.get_ptr(), numColsRational());
2736  }
2737  else
2738  {
2739  _idxToPerm(idx, n, perm, numColsRational());
2741  }
2742  }
2743 
2744 
2745 
2746  /// removes columns \p start to \p end including both; an array \p perm of size #numColsRational() may be passed as
2747  /// buffer memory
2748  void SoPlex::removeColRangeRational(int start, int end, int perm[])
2749  {
2750  if( perm == 0 )
2751  {
2753  _rangeToPerm(start, end, p.get_ptr(), numColsRational());
2755  }
2756  else
2757  {
2758  _rangeToPerm(start, end, perm, numColsRational());
2760  }
2761  }
2762 
2763 
2764 
2765  /// clears the LP
2767  {
2768  assert(_rationalLP != 0);
2769 
2771  return;
2772 
2773  _rationalLP->clear();
2775  _rowTypes.clear();
2776  _colTypes.clear();
2777 
2779  {
2780  _realLP->clear();
2781  _hasBasis = false;
2782  }
2783 
2785  }
2786 
2787 
2788 
2789  /// synchronizes rational LP with real LP, i.e., copies real LP to rational LP, if sync mode is manual
2791  {
2792  assert(_isConsistent());
2793 
2795  _syncLPRational();
2796  }
2797 
2798 
2799 
2800  /// solves the LP
2802  {
2803  assert(_isConsistent());
2804 
2805  // clear statistics
2807 
2808  // the solution is no longer valid
2810 
2811  // if the decomposition based dual simplex flag is set to true
2813  {
2817  //setBoolParam(SoPlex::PERSISTENTSCALING, false);
2818 
2820 
2822  }
2823  // decide whether to solve the rational LP with iterative refinement or call the standard floating-point solver
2825  && GE(realParam(SoPlex::FEASTOL), 1e-9) && GE(realParam(SoPlex::OPTTOL), 1e-9)) )
2826  {
2827  // ensure that tolerances are reasonable for the floating-point solver
2829  {
2830  MSG_WARNING( spxout, spxout << "Cannot call floating-point solver with feasibility tolerance below "
2831  << _currentSettings->realParam.lower[SoPlex::FPFEASTOL] << " - relaxing tolerance\n");
2833  }
2834  else
2836 
2838  {
2839  MSG_WARNING( spxout, spxout << "Cannot call floating-point solver with optimality tolerance below "
2840  << _currentSettings->realParam.lower[SoPlex::FPOPTTOL] << " - relaxing tolerance\n");
2842  }
2843  else
2845 
2847 
2848  _optimizeReal();
2849 #ifdef SOPLEX_DEBUG // this check will remove scaling of the realLP
2851 #endif
2852  }
2854  {
2855  _syncLPRational();
2857  }
2859  {
2860 #ifdef ENABLE_ADDITIONAL_CHECKS
2861  assert(areLPsInSync(true, true, false));
2862 #else
2863  assert(areLPsInSync(true, false, false));
2864 #endif
2865 
2867 
2868 #ifdef ENABLE_ADDITIONAL_CHECKS
2869  assert(areLPsInSync(true, true, false));
2870 #else
2871  assert(areLPsInSync(true, false, false));
2872 #endif
2873  }
2874  else
2875  {
2876 #ifdef ENABLE_ADDITIONAL_CHECKS
2877  assert(areLPsInSync(true, true, false));
2878 #else
2879  assert(areLPsInSync(true, false, false));
2880 #endif
2881 
2883  }
2884 
2885  MSG_INFO1( spxout, spxout << "\n";
2887  spxout << "\n" );
2888 
2889 
2890  return status();
2891  }
2892 
2893 
2894 
2895  /// returns the current solver status
2897  {
2898  return _status;
2899  }
2900 
2901 
2902 
2903  /// is stored primal solution feasible?
2905  {
2907  }
2908 
2909 
2910 
2911  /// is a primal feasible solution available?
2912  bool SoPlex::hasPrimal() const
2913  {
2914  return _hasSolReal || _hasSolRational;
2915  }
2916 
2917 
2918 
2919  /// is a primal unbounded ray available?
2921  {
2923  }
2924 
2925 
2926 
2927  /// is stored dual solution feasible?
2929  {
2931  }
2932 
2933 
2934 
2935  /// is a dual feasible solution available?
2936  bool SoPlex::hasDual() const
2937  {
2938  return _hasSolReal || _hasSolRational;
2939  }
2940 
2941 
2942 
2943  /// is Farkas proof of infeasibility available?
2945  {
2947  }
2948 
2949 
2950 
2951  /// returns the objective value if a primal or dual solution is available
2953  {
2954  assert(OBJSENSE_MAXIMIZE == 1);
2955  assert(OBJSENSE_MINIMIZE == -1);
2956 
2957  if( status() == SPxSolver::UNBOUNDED )
2959  else if( status() == SPxSolver::INFEASIBLE )
2961  else if( hasPrimal() || hasDual() )
2962  {
2964  return _solReal._objVal;
2965  }
2966  else
2967  return 0.0;
2968  }
2969 
2970 
2971 
2972  /// gets the primal solution vector if available; returns true on success
2974  {
2975  if( hasPrimal() && vector.dim() >= numColsReal() )
2976  {
2978  _solReal.getPrimal(vector);
2979  return true;
2980  }
2981  else
2982  return false;
2983  }
2984 
2985 
2986 
2987  /// gets the vector of slack values if available; returns true on success
2989  {
2990  if( hasPrimal() && vector.dim() >= numRowsReal() )
2991  {
2993  _solReal.getSlacks(vector);
2994  return true;
2995  }
2996  else
2997  return false;
2998  }
2999 
3000 
3001 
3002  /// gets the primal ray if available; returns true on success
3004  {
3005  if( hasPrimalRay() && vector.dim() >= numColsReal() )
3006  {
3008  _solReal.getPrimalRay(vector);
3009  return true;
3010  }
3011  else
3012  return false;
3013  }
3014 
3015 
3016 
3017  /// gets the dual solution vector if available; returns true on success
3019  {
3020  if( hasDual() && vector.dim() >= numRowsReal() )
3021  {
3023  _solReal.getDual(vector);
3024  return true;
3025  }
3026  else
3027  return false;
3028  }
3029 
3030 
3031 
3032  /// gets the vector of reduced cost values if available; returns true on success
3034  {
3035  if( hasDual() && vector.dim() >= numColsReal() )
3036  {
3038  _solReal.getRedCost(vector);
3039  return true;
3040  }
3041  else
3042  return false;
3043  }
3044 
3045 
3046 
3047  /// gets the Farkas proof if available; returns true on success
3049  {
3050  if( hasDualFarkas() && vector.dim() >= numRowsReal() )
3051  {
3053  _solReal.getDualFarkas(vector);
3054  return true;
3055  }
3056  else
3057  return false;
3058  }
3059 
3060 
3061 
3062  /// gets violation of bounds; returns true on success
3063  bool SoPlex::getBoundViolationReal(Real& maxviol, Real& sumviol)
3064  {
3065  if( !isPrimalFeasible() )
3066  return false;
3067 
3069  VectorReal& primal = _solReal._primal;
3070  assert(primal.dim() == numColsReal());
3071 
3072  maxviol = 0.0;
3073  sumviol = 0.0;
3074 
3075  for( int i = numColsReal() - 1; i >= 0; i-- )
3076  {
3077  Real lower = _realLP->lowerUnscaled(i);
3078  Real upper = _realLP->upperUnscaled(i);
3079  Real viol = lower - primal[i];
3080  if( viol > 0.0 )
3081  {
3082  sumviol += viol;
3083  if( viol > maxviol )
3084  maxviol = viol;
3085  }
3086 
3087  viol = primal[i] - upper;
3088  if( viol > 0.0 )
3089  {
3090  sumviol += viol;
3091  if( viol > maxviol )
3092  maxviol = viol;
3093  }
3094  }
3095 
3096  return true;
3097  }
3098 
3099 
3100 
3101  /// gets violation of constraints; returns true on success
3102  bool SoPlex::getRowViolationReal(Real& maxviol, Real& sumviol)
3103  {
3104  if( !isPrimalFeasible() )
3105  return false;
3106 
3108  VectorReal& primal = _solReal._primal;
3109  assert(primal.dim() == numColsReal());
3110 
3111  DVectorReal activity(numRowsReal());
3112  _realLP->computePrimalActivity(primal, activity, true);
3113  maxviol = 0.0;
3114  sumviol = 0.0;
3115 
3116  for( int i = numRowsReal() - 1; i >= 0; i-- )
3117  {
3118  Real lhs = _realLP->lhsUnscaled(i);
3119  Real rhs = _realLP->rhsUnscaled(i);
3120 
3121  Real viol = lhs - activity[i];
3122  if( viol > 0.0 )
3123  {
3124  sumviol += viol;
3125  if( viol > maxviol )
3126  maxviol = viol;
3127  }
3128 
3129  viol = activity[i] - rhs;
3130  if( viol > 0.0 )
3131  {
3132  sumviol += viol;
3133  if( viol > maxviol )
3134  maxviol = viol;
3135  }
3136  }
3137 
3138  return true;
3139  }
3140 
3141 
3142 
3143  /// gets violation of reduced costs; returns true on success
3144  bool SoPlex::getRedCostViolationReal(Real& maxviol, Real& sumviol)
3145  {
3146  if( !isDualFeasible() || !hasBasis() )
3147  return false;
3148 
3150  VectorReal& redcost = _solReal._redCost;
3151  assert(redcost.dim() == numColsReal());
3152 
3153  maxviol = 0.0;
3154  sumviol = 0.0;
3155 
3156  for( int c = numColsReal() - 1; c >= 0; c-- )
3157  {
3158  SPxSolver::VarStatus colStatus = basisColStatus(c);
3159 
3161  {
3162  if( colStatus != SPxSolver::ON_UPPER && colStatus != SPxSolver::FIXED && redcost[c] < 0.0 )
3163  {
3164  sumviol += -redcost[c];
3165  if( redcost[c] < -maxviol )
3166  maxviol = -redcost[c];
3167  }
3168  if( colStatus != SPxSolver::ON_LOWER && colStatus != SPxSolver::FIXED && redcost[c] > 0.0 )
3169  {
3170  sumviol += redcost[c];
3171  if( redcost[c] > maxviol )
3172  maxviol = redcost[c];
3173  }
3174  }
3175  else
3176  {
3177  if( colStatus != SPxSolver::ON_UPPER && colStatus != SPxSolver::FIXED && redcost[c] > 0.0 )
3178  {
3179  sumviol += redcost[c];
3180  if( redcost[c] > maxviol )
3181  maxviol = redcost[c];
3182  }
3183  if( colStatus != SPxSolver::ON_LOWER && colStatus != SPxSolver::FIXED && redcost[c] < 0.0 )
3184  {
3185  sumviol += -redcost[c];
3186  if( redcost[c] < -maxviol )
3187  maxviol = -redcost[c];
3188  }
3189  }
3190  }
3191 
3192  return true;
3193  }
3194 
3195 
3196 
3197  /// gets violation of dual multipliers; returns true on success
3198  bool SoPlex::getDualViolationReal(Real& maxviol, Real& sumviol)
3199  {
3200  if( !isDualFeasible() || !hasBasis() )
3201  return false;
3202 
3204  VectorReal& dual = _solReal._dual;
3205  assert(dual.dim() == numRowsReal());
3206 
3207  maxviol = 0.0;
3208  sumviol = 0.0;
3209 
3210  for( int r = numRowsReal() - 1; r >= 0; r-- )
3211  {
3212  SPxSolver::VarStatus rowStatus = basisRowStatus(r);
3213 
3215  {
3216  if( rowStatus != SPxSolver::ON_UPPER && rowStatus != SPxSolver::FIXED && dual[r] < 0.0 )
3217  {
3218  sumviol += -dual[r];
3219  if( dual[r] < -maxviol )
3220  maxviol = -dual[r];
3221  }
3222  if( rowStatus != SPxSolver::ON_LOWER && rowStatus != SPxSolver::FIXED && dual[r] > 0.0 )
3223  {
3224  sumviol += dual[r];
3225  if( dual[r] > maxviol )
3226  maxviol = dual[r];
3227  }
3228  }
3229  else
3230  {
3231  if( rowStatus != SPxSolver::ON_UPPER && rowStatus != SPxSolver::FIXED && dual[r] > 0.0 )
3232  {
3233  sumviol += dual[r];
3234  if( dual[r] > maxviol )
3235  maxviol = dual[r];
3236  }
3237  if( rowStatus != SPxSolver::ON_LOWER && rowStatus != SPxSolver::FIXED && dual[r] < 0.0 )
3238  {
3239  sumviol += -dual[r];
3240  if( dual[r] < -maxviol )
3241  maxviol = -dual[r];
3242  }
3243  }
3244  }
3245 
3246  return true;
3247  }
3248 
3249 
3250 
3251  /// returns the objective value if a primal or dual solution is available
3253  {
3254  assert(OBJSENSE_MAXIMIZE == 1);
3255  assert(OBJSENSE_MINIMIZE == -1);
3256 
3257  if( status() == SPxSolver::UNBOUNDED )
3258  {
3260  return _rationalPosInfty;
3261  else
3262  return _rationalNegInfty;
3263  }
3264  else if( status() == SPxSolver::INFEASIBLE )
3265  {
3267  return _rationalNegInfty;
3268  else
3269  return _rationalPosInfty;
3270  }
3271  else if( hasPrimal() || hasDual() )
3272  {
3274  return _solRational._objVal;
3275  }
3276  else
3277  return _rationalZero;
3278  }
3279 
3280 
3281 
3282  /// gets the primal solution vector if available; returns true on success
3284  {
3285  if( _rationalLP != 0 && hasPrimal() && vector.dim() >= numColsRational() )
3286  {
3288  _solRational.getPrimal(vector);
3289  return true;
3290  }
3291  else
3292  return false;
3293  }
3294 
3295 
3296 
3297  /// gets the vector of slack values if available; returns true on success
3299  {
3300  if( _rationalLP != 0 && hasPrimal() && vector.dim() >= numRowsRational() )
3301  {
3303  _solRational.getSlacks(vector);
3304  return true;
3305  }
3306  else
3307  return false;
3308  }
3309 
3310 
3311 
3312  /// gets the primal ray if LP is unbounded; returns true on success
3314  {
3315  if( _rationalLP != 0 && hasPrimalRay() && vector.dim() >= numColsRational() )
3316  {
3318  _solRational.getPrimalRay(vector);
3319  return true;
3320  }
3321  else
3322  return false;
3323  }
3324 
3325 
3326 
3327  /// gets the dual solution vector if available; returns true on success
3329  {
3330  if( _rationalLP != 0 && hasDual() && vector.dim() >= numRowsRational() )
3331  {
3333  _solRational.getDual(vector);
3334  return true;
3335  }
3336  else
3337  return false;
3338  }
3339 
3340 
3341 
3342  /// gets the vector of reduced cost values if available; returns true on success
3344  {
3345  if( _rationalLP != 0 && hasDual() && vector.dim() >= numColsRational() )
3346  {
3348  _solRational.getRedCost(vector);
3349  return true;
3350  }
3351  else
3352  return false;
3353  }
3354 
3355 
3356 
3357  /// gets the Farkas proof if LP is infeasible; returns true on success
3359  {
3360  if( _rationalLP != 0 && hasDualFarkas() && vector.dim() >= numRowsRational() )
3361  {
3363  _solRational.getDualFarkas(vector);
3364  return true;
3365  }
3366  else
3367  return false;
3368  }
3369 
3370 
3371 
3372  /// gets violation of bounds; returns true on success
3374  {
3375  if( !isPrimalFeasible() )
3376  return false;
3377 
3378  // if we have to synchronize, we do not measure time, because this would affect the solving statistics
3380  _syncLPRational(false);
3381 
3384  assert(primal.dim() == numColsRational());
3385 
3386  maxviol = 0;
3387  sumviol = 0;
3388 
3389  for( int i = numColsRational() - 1; i >= 0; i-- )
3390  {
3391  Rational viol = lowerRational(i) - primal[i];
3392  if( viol > 0 )
3393  {
3394  sumviol += viol;
3395  if( viol > maxviol )
3396  {
3397  maxviol = viol;
3398  MSG_DEBUG( std::cout << "increased bound violation for column " << i << ": " << rationalToString(viol)
3399  << " lower: " << rationalToString(lowerRational(i))
3400  << ", primal: " << rationalToString(primal[i]) << "\n" );
3401  }
3402  }
3403 
3404  viol = primal[i] - upperRational(i);
3405  if( viol > 0 )
3406  {
3407  sumviol += viol;
3408  if( viol > maxviol )
3409  {
3410  maxviol = viol;
3411  MSG_DEBUG( std::cout << "increased bound violation for column " << i << ": " << rationalToString(viol)
3412  << " upper: " << rationalToString(upperRational(i))
3413  << ", primal: " << rationalToString(primal[i]) << "\n" );
3414  }
3415  }
3416  }
3417 
3418  return true;
3419  }
3420 
3421 
3422 
3423  /// gets violation of constraints; returns true on success
3425  {
3426  if( !isPrimalFeasible() )
3427  return false;
3428 
3429  // if we have to synchronize, we do not measure time, because this would affect the solving statistics
3431  _syncLPRational(false);
3432 
3435  assert(primal.dim() == numColsRational());
3436 
3437  DVectorRational activity(numRowsRational());
3438  _rationalLP->computePrimalActivity(primal, activity);
3439  maxviol = 0;
3440  sumviol = 0;
3441 
3442  for( int i = numRowsRational() - 1; i >= 0; i-- )
3443  {
3444  Rational viol = lhsRational(i) - activity[i];
3445  if( viol > 0 )
3446  {
3447  sumviol += viol;
3448  if( viol > maxviol )
3449  {
3450  maxviol = viol;
3451  MSG_DEBUG( std::cout << "increased constraint violation for row " << i << ": " << rationalToString(viol)
3452  << " lhs: " << rationalToString(lhsRational(i))
3453  << ", activity: " << rationalToString(activity[i]) << "\n" );
3454  }
3455  }
3456 
3457  viol = activity[i] - rhsRational(i);
3458  if( viol > 0 )
3459  {
3460  sumviol += viol;
3461  if( viol > maxviol )
3462  {
3463  maxviol = viol;
3464  MSG_DEBUG( std::cout << "increased constraint violation for row " << i << ": " << rationalToString(viol)
3465  << " rhs: " << rationalToString(rhsRational(i))
3466  << ", activity: " << rationalToString(activity[i]) << "\n" );
3467  }
3468  }
3469  }
3470 
3471  return true;
3472  }
3473 
3474 
3475 
3476  /// gets violation of reduced costs; returns true on success
3478  {
3479  if( !isPrimalFeasible() || !isDualFeasible() )
3480  return false;
3481 
3482  // if we have to synchronize, we do not measure time, because this would affect the solving statistics
3484  _syncLPRational(false);
3485 
3488  assert(redcost.dim() == numColsRational());
3489 
3490  maxviol = 0;
3491  sumviol = 0;
3492 
3493  for( int c = numColsReal() - 1; c >= 0; c-- )
3494  {
3495  assert(!_hasBasis || basisColStatus(c) != SPxSolver::UNDEFINED);
3496 
3497  if( _colTypes[c] == RANGETYPE_FIXED )
3498  {
3499  assert(lowerRational(c) == upperRational(c));
3500  continue;
3501  }
3502 
3507 
3509  {
3510  if( _solRational._primal[c] != upperRational(c) && redcost[c] < 0 )
3511  {
3512  sumviol += -redcost[c];
3513  if( redcost[c] < -maxviol )
3514  {
3515  MSG_DEBUG( std::cout << "increased reduced cost violation for column " << c << " not on upper bound: " << rationalToString(-redcost[c]) << "\n" );
3516  maxviol = -redcost[c];
3517  }
3518  }
3519  if( _solRational._primal[c] != lowerRational(c) && redcost[c] > 0 )
3520  {
3521  sumviol += redcost[c];
3522  if( redcost[c] > maxviol )
3523  {
3524  MSG_DEBUG( std::cout << "increased reduced cost violation for column " << c << " not on lower bound: " << rationalToString(redcost[c]) << "\n" );
3525  maxviol = redcost[c];
3526  }
3527  }
3528  }
3529  else
3530  {
3531  if( _solRational._primal[c] != upperRational(c) && redcost[c] > 0 )
3532  {
3533  sumviol += redcost[c];
3534  if( redcost[c] > maxviol )
3535  {
3536  MSG_DEBUG( std::cout << "increased reduced cost violation for column " << c << " not on upper bound: " << rationalToString(redcost[c]) << "\n" );
3537  maxviol = redcost[c];
3538  }
3539  }
3540  if( _solRational._primal[c] != lowerRational(c) && redcost[c] < 0 )
3541  {
3542  sumviol += -redcost[c];
3543  if( redcost[c] < -maxviol )
3544  {
3545  MSG_DEBUG( std::cout << "increased reduced cost violation for column " << c << " not on lower bound: " << rationalToString(-redcost[c]) << "\n" );
3546  maxviol = -redcost[c];
3547  }
3548  }
3549  }
3550  }
3551 
3552  return true;
3553  }
3554 
3555 
3556 
3557  /// gets violation of dual multipliers; returns true on success
3559  {
3560  if( !isDualFeasible() || !isPrimalFeasible() )
3561  return false;
3562 
3563  // if we have to synchronize, we do not measure time, because this would affect the solving statistics
3565  _syncLPRational(false);
3566 
3569  assert(dual.dim() == numRowsRational());
3570 
3571  maxviol = 0;
3572  sumviol = 0;
3573 
3574  for( int r = numRowsReal() - 1; r >= 0; r-- )
3575  {
3576  assert(!_hasBasis || basisRowStatus(r) != SPxSolver::UNDEFINED);
3577 
3578  if( _rowTypes[r] == RANGETYPE_FIXED )
3579  {
3580  assert(lhsRational(r) == rhsRational(r));
3581  continue;
3582  }
3583 
3588 
3590  {
3591  if( _solRational._slacks[r] < rhsRational(r) - _rationalFeastol && dual[r] < 0 )
3592  {
3593  sumviol += -dual[r];
3594  if( dual[r] < -maxviol )
3595  {
3596  MSG_DEBUG( std::cout << "increased dual violation for row " << r << " not on upper bound: " << rationalToString(-dual[r])
3597  << " (slack = " << rationalToString(_solRational._slacks[r])
3598  << ", status = " << basisRowStatus(r)
3599  << ", lhs = " << rationalToString(lhsRational(r))
3600  << ", rhs = " << rationalToString(rhsRational(r)) << ")\n" );
3601  maxviol = -dual[r];
3602  }
3603  }
3604  if( _solRational._slacks[r] > lhsRational(r) + _rationalFeastol && dual[r] > 0 )
3605  {
3606  sumviol += dual[r];
3607  if( dual[r] > maxviol )
3608  {
3609  MSG_DEBUG( std::cout << "increased dual violation for row " << r << " not on lower bound: " << rationalToString(dual[r])
3610  << " (slack = " << rationalToString(_solRational._slacks[r])
3611  << ", status = " << basisRowStatus(r)
3612  << ", lhs = " << rationalToString(lhsRational(r))
3613  << ", rhs = " << rationalToString(rhsRational(r)) << ")\n" );
3614  maxviol = dual[r];
3615  }
3616  }
3617  }
3618  else
3619  {
3620  if( _solRational._slacks[r] < rhsRational(r) - _rationalFeastol && dual[r] > 0 )
3621  {
3622  sumviol += dual[r];
3623  if( dual[r] > maxviol )
3624  {
3625  MSG_DEBUG( std::cout << "increased dual violation for row " << r << " not on upper bound: " << rationalToString(dual[r])
3626  << " (slack = " << rationalToString(_solRational._slacks[r])
3627  << ", status = " << basisRowStatus(r)
3628  << ", lhs = " << rationalToString(lhsRational(r))
3629  << ", rhs = " << rationalToString(rhsRational(r)) << ")\n" );
3630  maxviol = dual[r];
3631  }
3632  }
3633  if( _solRational._slacks[r] > lhsRational(r) + _rationalFeastol && dual[r] < 0 )
3634  {
3635  sumviol += -dual[r];
3636  if( dual[r] < -maxviol )
3637  {
3638  MSG_DEBUG( std::cout << "increased dual violation for row " << r << " not on lower bound: " << rationalToString(-dual[r])
3639  << " (slack = " << rationalToString(_solRational._slacks[r])
3640  << ", status = " << basisRowStatus(r)
3641  << ", lhs = " << rationalToString(lhsRational(r))
3642  << ", rhs = " << rationalToString(rhsRational(r)) << ")\n" );
3643  maxviol = -dual[r];
3644  }
3645  }
3646  }
3647  }
3648 
3649  return true;
3650  }
3651 
3652 
3653 
3654 #ifdef SOPLEX_WITH_GMP
3655  /// gets the primal solution vector if available; returns true on success
3656  bool SoPlex::getPrimalRational(mpq_t* vector, const int size)
3657  {
3658  assert(size >= numColsRational());
3659 
3660  if( hasPrimal() )
3661  {
3663  for( int i = 0; i < numColsRational(); i++ )
3664  mpq_set(vector[i], _solRational._primal[i].getMpqRef());
3665  return true;
3666  }
3667  else
3668  return false;
3669  }
3670 
3671 
3672  /// gets the vector of slack values if available; returns true on success
3673  bool SoPlex::getSlacksRational(mpq_t* vector, const int size)
3674  {
3675  assert(size >= numRowsRational());
3676 
3677  if( hasPrimal() )
3678  {
3680  for( int i = 0; i < numRowsRational(); i++ )
3681  mpq_set(vector[i], _solRational._slacks[i].getMpqRef());
3682  return true;
3683  }
3684  else
3685  return false;
3686  }
3687 
3688 
3689 
3690  /// gets the primal ray if LP is unbounded; returns true on success
3691  bool SoPlex::getPrimalRayRational(mpq_t* vector, const int size)
3692  {
3693  assert(size >= numColsRational());
3694 
3695  if( hasPrimalRay() )
3696  {
3698  for( int i = 0; i < numColsRational(); i++ )
3699  mpq_set(vector[i], _solRational._primalRay[i].getMpqRef());
3700  return true;
3701  }
3702  else
3703  return false;
3704  }
3705 
3706 
3707 
3708  /// gets the dual solution vector if available; returns true on success
3709  bool SoPlex::getDualRational(mpq_t* vector, const int size)
3710  {
3711  assert(size >= numRowsRational());
3712 
3713  if( hasDual() )
3714  {
3716  for( int i = 0; i < numRowsRational(); i++ )
3717  mpq_set(vector[i], _solRational._dual[i].getMpqRef());
3718  return true;
3719  }
3720  else
3721  return false;
3722  }
3723 
3724 
3725 
3726  /// gets the vector of reduced cost values if available; returns true on success
3727  bool SoPlex::getRedCostRational(mpq_t* vector, const int size)
3728  {
3729  assert(size >= numColsRational());
3730 
3731  if( hasDual() )
3732  {
3734  for( int i = 0; i < numColsRational(); i++ )
3735  mpq_set(vector[i], _solRational._redCost[i].getMpqRef());
3736  return true;
3737  }
3738  else
3739  return false;
3740  }
3741 
3742 
3743 
3744  /// gets the Farkas proof if LP is infeasible; returns true on success
3745  bool SoPlex::getDualFarkasRational(mpq_t* vector, const int size)
3746  {
3747  assert(size >= numRowsRational());
3748 
3749  if( hasDualFarkas() )
3750  {
3752  for( int i = 0; i < numRowsRational(); i++ )
3753  mpq_set(vector[i], _solRational._dualFarkas[i].getMpqRef());
3754  return true;
3755  }
3756  else
3757  return false;
3758  }
3759 #endif
3760 
3761 
3762 
3763  /// get size of primal solution
3765  {
3766  if( hasPrimal() || hasPrimalRay() )
3767  {
3769  return _solRational.totalSizePrimal(base);
3770  }
3771  else
3772  return 0;
3773  }
3774 
3775 
3776 
3777  /// get size of dual solution
3778  int SoPlex::totalSizeDualRational(const int base)
3779  {
3780  if( hasDual() || hasDualFarkas() )
3781  {
3783  return _solRational.totalSizeDual(base);
3784  }
3785  else
3786  return 0;
3787  }
3788 
3789 
3790 
3791  /// get size of least common multiple of denominators in primal solution
3793  {
3794  if( hasPrimal() || hasPrimalRay() )
3795  {
3797  return _solRational.dlcmSizePrimal(base);
3798  }
3799  else
3800  return 0;
3801  }
3802 
3803 
3804 
3805  /// get size of least common multiple of denominators in dual solution
3806  int SoPlex::dlcmSizeDualRational(const int base)
3807  {
3808  if( hasDual() || hasDualFarkas() )
3809  {
3811  return _solRational.dlcmSizeDual(base);
3812  }
3813  else
3814  return 0;
3815  }
3816 
3817 
3818 
3819  /// get size of largest denominator in primal solution
3821  {
3822  if( hasPrimal() || hasPrimalRay() )
3823  {
3825  return _solRational.dmaxSizePrimal(base);
3826  }
3827  else
3828  return 0;
3829  }
3830 
3831 
3832 
3833  /// get size of largest denominator in dual solution
3834  int SoPlex::dmaxSizeDualRational(const int base)
3835  {
3836  if( hasDual() || hasDualFarkas() )
3837  {
3839  return _solRational.dmaxSizeDual(base);
3840  }
3841  else
3842  return 0;
3843  }
3844 
3845 
3846 
3847  /// is an advanced starting basis available?
3848  bool SoPlex::hasBasis() const
3849  {
3850  return _hasBasis;
3851  }
3852 
3853 
3854 
3855  /// returns the current basis status
3857  {
3858  if( !hasBasis() )
3859  return SPxBasis::NO_PROBLEM;
3860  else if( status() == SPxSolver::OPTIMAL )
3861  return SPxBasis::OPTIMAL;
3862  else if( status() == SPxSolver::UNBOUNDED )
3863  return SPxBasis::UNBOUNDED;
3864  else if( status() == SPxSolver::INFEASIBLE )
3865  return SPxBasis::INFEASIBLE;
3866  else if( hasPrimal() )
3867  return SPxBasis::PRIMAL;
3868  else if( hasDual() )
3869  return SPxBasis::DUAL;
3870  else
3871  return SPxBasis::REGULAR;
3872  }
3873 
3874 
3875 
3876  /// returns basis status for a single row
3878  {
3879  assert(row >= 0);
3880  assert(row < numRowsReal());
3881 
3882  // if no basis is available, return slack basis; if index is out of range, return basic status as for a newly
3883  // added row
3884  if( !hasBasis() || row < 0 || row >= numRowsReal() )
3885  return SPxSolver::BASIC;
3886  // if the real LP is loaded, ask solver
3887  else if( _isRealLPLoaded )
3888  {
3889  return _solver.getBasisRowStatus(row);
3890  }
3891  // if the real LP is not loaded, the basis is stored in the basis arrays of this class
3892  else
3893  {
3894  assert(row < _basisStatusRows.size());
3895  return _basisStatusRows[row];
3896  }
3897  }
3898 
3899 
3900 
3901  /// returns basis status for a single column
3903  {
3904  assert(col >= 0);
3905  assert(col < numColsReal());
3906 
3907  // if index is out of range, return nonbasic status as for a newly added unbounded column
3908  if( col < 0 || col >= numColsReal() )
3909  {
3910  return SPxSolver::ZERO;
3911  }
3912  // if no basis is available, return slack basis
3913  else if( !hasBasis() )
3914  {
3915  if( lowerReal(col) > -realParam(SoPlex::INFTY) )
3916  return SPxSolver::ON_LOWER;
3917  else if( upperReal(col) < realParam(SoPlex::INFTY) )
3918  return SPxSolver::ON_UPPER;
3919  else
3920  return SPxSolver::ZERO;
3921  }
3922  // if the real LP is loaded, ask solver
3923  else if( _isRealLPLoaded )
3924  {
3925  return _solver.getBasisColStatus(col);
3926  }
3927  // if the real LP is not loaded, the basis is stored in the basis arrays of this class
3928  else
3929  {
3930  assert(col < _basisStatusCols.size());
3931  return _basisStatusCols[col];
3932  }
3933  }
3934 
3935 
3936 
3937  /// gets current basis
3939  {
3940  // if no basis is available, return slack basis
3941  if( !hasBasis() )
3942  {
3943  for( int i = numRowsReal() - 1; i >= 0; i-- )
3944  rows[i] = SPxSolver::BASIC;
3945 
3946  for( int i = numColsReal() - 1; i >= 0; i-- )
3947  {
3948  if( lowerReal(i) > -realParam(SoPlex::INFTY) )
3949  cols[i] = SPxSolver::ON_LOWER;
3950  else if( upperReal(i) < realParam(SoPlex::INFTY) )
3951  cols[i] = SPxSolver::ON_UPPER;
3952  else
3953  cols[i] = SPxSolver::ZERO;
3954  }
3955  }
3956  // if the real LP is loaded, ask solver
3957  else if( _isRealLPLoaded )
3958  {
3959  (void)_solver.getBasis(rows, cols);
3960  }
3961  // if the real LP is not loaded, the basis is stored in the basis arrays of this class
3962  else
3963  {
3964  assert(numRowsReal() == _basisStatusRows.size());
3965  assert(numColsReal() == _basisStatusCols.size());
3966 
3967  for( int i = numRowsReal() - 1; i >= 0; i-- )
3968  rows[i] = _basisStatusRows[i];
3969 
3970  for( int i = numColsReal() - 1; i >= 0; i-- )
3971  cols[i] = _basisStatusCols[i];
3972  }
3973  }
3974 
3975 
3976 
3977  /// returns the indices of the basic columns and rows; basic column n gives value n, basic row m gives value -1-m
3978  void SoPlex::getBasisInd(int* bind) const
3979  {
3980  // if no basis is available, return slack basis
3981  if( !hasBasis() )
3982  {
3983  for( int i = 0; i < numRowsReal(); ++i )
3984  bind[i] = -1 - i;
3985  }
3986  // if the real LP is not loaded, the basis is stored in the basis arrays of this class
3987  else if( !_isRealLPLoaded )
3988  {
3989  int k = 0;
3990 
3991  assert(numRowsReal() == _basisStatusRows.size());
3992  assert(numColsReal() == _basisStatusCols.size());
3993 
3994  for( int i = 0; i < numRowsReal(); ++i )
3995  {
3997  {
3998  bind[k] = -1 - i;
3999  k++;
4000  }
4001  }
4002 
4003  for( int j = 0; j < numColsReal(); ++j )
4004  {
4006  {
4007  bind[k] = j;
4008  k++;
4009  }
4010  }
4011 
4012  assert(k == numRowsReal());
4013  }
4014  // if the real LP is loaded, the basis is stored in the solver and we need to distinguish between column and row
4015  // representation; ask the solver itself which representation it has, since the REPRESENTATION parameter of this
4016  // class might be set to automatic
4017  else if( _solver.rep() == SPxSolver::COLUMN )
4018  {
4019  for( int i = 0; i < numRowsReal(); ++i )
4020  {
4021  SPxId id = _solver.basis().baseId(i);
4022  bind[i] = (id.isSPxColId() ? _solver.number(id) : - 1 - _solver.number(id));
4023  }
4024  }
4025  // for row representation, return the complement of the row basis; for this, we need to loop through all rows and columns
4026  else
4027  {
4028  assert(_solver.rep() == SPxSolver::ROW);
4029 
4030  int k = 0;
4031 
4032  for( int i = 0; i < numRowsReal(); ++i )
4033  {
4034  if( !_solver.isRowBasic(i) )
4035  {
4036  bind[k] = -1 - i;
4037  k++;
4038  }
4039  }
4040 
4041  for( int j = 0; j < numColsReal(); ++j )
4042  {
4043  if( !_solver.isColBasic(j) )
4044  {
4045  bind[k] = j;
4046  k++;
4047  }
4048  }
4049 
4050  assert(k == numRowsReal());
4051  }
4052  }
4053 
4054 
4055  /// compute condition number estimate based on the diagonal of the LU factorization; returns true on success
4056  /// type = 0: max/min ratio
4057  /// type = 1: trace of U (sum of diagonal elements)
4058  /// type = 2: product of diagonal elements
4059  bool SoPlex::getFastCondition(Real& condition, int type)
4060  {
4062  if( !_isRealLPLoaded )
4063  return false;
4064 
4066  return false;
4067 
4068  condition = _solver.basis().getFastCondition(type);
4069 
4070  return true;
4071  }
4072 
4073  /// computes an estimated condition number for the current basis matrix using the power method; returns true on success
4075  {
4077  if( !_isRealLPLoaded )
4078  return false;
4079 
4081  return false;
4082 
4083  condition = _solver.basis().getEstimatedCondition();
4084 
4085  return true;
4086  }
4087 
4088  /// computes the exact condition number for the current basis matrix using the power method; returns true on success
4090  {
4092  if( !_isRealLPLoaded )
4093  return false;
4094 
4096  return false;
4097 
4098  condition = _solver.basis().getExactCondition();
4099 
4100  return true;
4101  }
4102 
4103  /// computes row r of basis inverse; returns true on success
4104  bool SoPlex::getBasisInverseRowReal(int r, Real* coef, int* inds, int* ninds, bool unscale)
4105  {
4106  assert(r >= 0);
4107  assert(r < numRowsReal());
4108  assert(coef != 0);
4109 
4110  if( !hasBasis() || r < 0 || r >= numRowsReal() )
4111  return false;
4112 
4114 
4115  if( !_isRealLPLoaded )
4116  return false;
4117 
4118  // we need to distinguish between column and row representation; ask the solver itself which representation it
4119  // has, since the REPRESENTATION parameter of this class might be set to automatic
4120  if( _solver.rep() == SPxSolver::COLUMN )
4121  {
4122  int idx;
4124  try
4125  {
4126  /* unscaling required? */
4127  if( unscale && _solver.isScaled())
4128  {
4129  /* for information on the unscaling procedure see spxscaler.h */
4130 
4131  int scaleExp;
4132  DSVector rhs(_solver.unitVector(r));
4133 
4134  if( _solver.basis().baseId(r).isSPxColId() )
4136  else
4137  scaleExp = - _scaler->getRowScaleExp(_solver.number(_solver.basis().baseId(r)));
4138 
4139  rhs *= spxLdexp(1.0, scaleExp);
4140 
4141  _solver.basis().coSolve(x, rhs);
4142  x.setup();
4143  int size = x.size();
4144 
4145  for( int i = 0; i < size; i++ )
4146  {
4147  scaleExp = _scaler->getRowScaleExp(x.index(i));
4148  x.scaleValue(x.index(i), scaleExp);
4149  }
4150  }
4151  else
4152  {
4154  }
4155  }
4156  catch( const SPxException& E )
4157  {
4158  MSG_INFO1( spxout, spxout << "Caught exception <" << E.what() << "> while computing basis inverse row.\n" );
4159  return false;
4160  }
4161  // copy sparse data to dense result vector based on coef array
4162  if( ninds != 0 && inds != 0 )
4163  {
4164  // during solving SoPlex may have destroyed the sparsity structure so we need to restore it
4165  x.setup();
4166  *ninds = x.size();
4167  for( int i = 0; i < *ninds; ++i )
4168  {
4169  idx = x.index(i);
4170  coef[idx] = x[idx];
4171  // set sparsity pattern of coef array
4172  inds[i] = idx;
4173  }
4174  }
4175  else
4176  {
4177  VectorReal y(numRowsReal(), coef);
4178  y = x;
4179  if( ninds != NULL )
4180  *ninds = -1;
4181  }
4182  }
4183  else
4184  {
4185  assert(_solver.rep() == SPxSolver::ROW);
4186 
4187  // @todo should rhs be a reference?
4188  DSVector rhs(numColsReal());
4189  SSVector y(numColsReal());
4190  int* bind = 0;
4191  int index;
4192 
4193  // get ordering of column basis matrix
4194  spx_alloc(bind, numRowsReal());
4195  getBasisInd(bind);
4196 
4197  // get vector corresponding to requested index r
4198  index = bind[r];
4199 
4200  // r corresponds to a row vector
4201  if( index < 0 )
4202  {
4203  // transform index to actual row index
4204  index = -index - 1;
4205 
4206  // should be a valid row index and in the column basis matrix, i.e., not basic w.r.t. row representation
4207  assert(index >= 0);
4208  assert(index < numRowsReal());
4209  assert(!_solver.isRowBasic(index));
4210 
4211  // get row vector
4212  rhs = _solver.rowVector(index);
4213  rhs *= -1.0;
4214 
4215  if( unscale && _solver.isScaled() )
4216  {
4217  for( int i = 0; i < rhs.size(); ++i)
4218  rhs.value(i) = spxLdexp(rhs.value(i), -_scaler->getRowScaleExp(index));
4219  }
4220  }
4221  // r corresponds to a column vector
4222  else
4223  {
4224  // should be a valid column index and in the column basis matrix, i.e., not basic w.r.t. row representation
4225  assert(index < numColsReal());
4226  assert(!_solver.isColBasic(index));
4227 
4228  // get unit vector
4229  rhs = UnitVectorReal(index);
4230 
4231  if( unscale && _solver.isScaled() )
4232  rhs *= spxLdexp(1.0, _scaler->getColScaleExp(index));
4233  }
4234 
4235  // solve system "y B = rhs", where B is the row basis matrix
4236  try
4237  {
4238  _solver.basis().solve(y, rhs);
4239  }
4240  catch( const SPxException& E )
4241  {
4242  MSG_INFO1( spxout, spxout << "Caught exception <" << E.what() << "> while computing basis inverse row.\n" );
4243  return false;
4244  }
4245 
4246  // initialize result vector x as zero
4247  memset(coef, 0, (unsigned int)numRowsReal() * sizeof(Real));
4248 
4249  // add nonzero entries
4250  for( int i = 0; i < numColsReal(); ++i )
4251  {
4252  SPxId id = _solver.basis().baseId(i);
4253 
4254  if( id.isSPxRowId() )
4255  {
4256  assert(_solver.number(id) >= 0);
4257  assert(_solver.number(id) < numRowsReal());
4258  assert(bind[r] >= 0 || _solver.number(id) != index);
4259 
4260  int rowindex = _solver.number(id);
4261  coef[rowindex] = y[i];
4262 
4263  if( unscale && _solver.isScaled() )
4264  coef[rowindex] = spxLdexp(y[i], _scaler->getRowScaleExp(rowindex));
4265  }
4266  }
4267 
4268  // if r corresponds to a row vector, we have to add a 1 at position r
4269  if( bind[r] < 0 )
4270  {
4271  assert(coef[index] == 0.0);
4272  coef[index] = 1.0;
4273  }
4274 
4275  // @todo implement returning of sparsity information like in column wise case
4276  if( ninds != NULL)
4277  *ninds = -1;
4278 
4279  // free memory
4280  spx_free(bind);
4281  }
4282 
4283  return true;
4284  }
4285 
4286 
4287 
4288  /// computes column c of basis inverse; returns true on success
4289  /// @todo does not work correctly for the row representation
4290  bool SoPlex::getBasisInverseColReal(int c, Real* coef, int* inds, int* ninds, bool unscale)
4291  {
4292  assert(c >= 0);
4293  assert(c < numRowsReal());
4294  assert(coef != 0);
4295 
4296  if( !hasBasis() || c < 0 || c >= numRowsReal() )
4297  return false;
4298 
4300 
4301  if( !_isRealLPLoaded )
4302  return false;
4303 
4304  // we need to distinguish between column and row representation; ask the solver itself which representation it
4305  // has, since the REPRESENTATION parameter of this class might be set to automatic
4306  if( _solver.rep() == SPxSolver::COLUMN )
4307  {
4308  int idx;
4310  try
4311  {
4312  /* unscaling required? */
4313  if( unscale && _solver.isScaled())
4314  {
4315  /* for information on the unscaling procedure see spxscaler.h */
4316 
4317  int scaleExp =_scaler->getRowScaleExp(c);
4318  DSVector rhs(_solver.unitVector(c));
4319  rhs *= spxLdexp(1.0, scaleExp);
4320 
4321  _solver.basis().solve(x, rhs);
4322 
4323  x.setup();
4324  int size = x.size();
4325 
4326  for( int i = 0; i < size; i++ )
4327  {
4328  if( _solver.basis().baseId(x.index(i)).isSPxColId() )
4329  {
4330  idx = _solver.number(_solver.basis().baseId(x.index(i)));
4331  scaleExp = _scaler->getColScaleExp(idx);
4332  x.scaleValue(x.index(i), scaleExp);
4333  }
4334  else
4335  {
4336  idx = _solver.number(_solver.basis().baseId(x.index(i)));
4337  scaleExp = - _scaler->getRowScaleExp(idx);
4338  x.scaleValue(x.index(i), scaleExp);
4339  }
4340  }
4341  }
4342  else
4343  {
4345  }
4346  }
4347  catch( const SPxException& E )
4348  {
4349  MSG_INFO1( spxout, spxout << "Caught exception <" << E.what() << "> while computing basis inverse row.\n" );
4350  return false;
4351  }
4352  // copy sparse data to dense result vector based on coef array
4353  if( ninds != 0 && inds != 0 )
4354  {
4355  // SoPlex may have destroyed the sparsity structure so we need to restore it
4356  x.setup();
4357  *ninds = x.size();
4358  for( int i = 0; i < *ninds; ++i )
4359  {
4360  idx = x.index(i);
4361  coef[idx] = x[idx];
4362  // set sparsity pattern of coef array
4363  inds[i] = idx;
4364  }
4365  }
4366  else
4367  {
4368  VectorReal y(numRowsReal(), coef);
4369  y = x;
4370  if( ninds != 0 )
4371  *ninds = -1;
4372  }
4373  }
4374  else
4375  {
4376  assert(_solver.rep() == SPxSolver::ROW);
4377 
4378  // @todo should rhs be a reference?
4379  DSVectorReal rhs(numColsReal());
4381  int* bind = 0;
4382  int index;
4383 
4384  // get ordering of column basis matrix
4385  spx_alloc(bind, numRowsReal());
4386  getBasisInd(bind);
4387 
4388  // get vector corresponding to requested index c
4389  index = bind[c];
4390 
4391  // c corresponds to a row vector
4392  if( index < 0 )
4393  {
4394  // transform index to actual row index
4395  index = -index - 1;
4396 
4397  // should be a valid row index and in the column basis matrix, i.e., not basic w.r.t. row representation
4398  assert(index >= 0);
4399  assert(index < numRowsReal());
4400  assert(!_solver.isRowBasic(index));
4401 
4402  // get row vector
4403  rhs = _solver.rowVector(index);
4404  rhs *= -1.0;
4405  }
4406  // c corresponds to a column vector
4407  else
4408  {
4409  // should be a valid column index and in the column basis matrix, i.e., not basic w.r.t. row representation
4410  assert(index < numColsReal());
4411  assert(!_solver.isColBasic(index));
4412 
4413  // get unit vector
4414  rhs = UnitVectorReal(index);
4415  }
4416 
4417  // solve system "y B = rhs", where B is the row basis matrix
4418  try
4419  {
4420  /* unscaling required? */
4421  if( unscale && _solver.isScaled() )
4422  {
4423  int size = rhs.size();
4424  int scaleExp;
4425 
4426  for( int i = 0; i < size; i++ )
4427  {
4428  scaleExp = _scaler->getColScaleExp(i);
4429  rhs.value(i) *= spxLdexp(1.0, scaleExp);
4430  }
4431 
4432  _solver.basis().coSolve(y, rhs);
4433 
4434  int rowIdx;
4435  size = y.size();
4436 
4437  for( int i = 0; i < size; i++ )
4438  {
4439  assert(_solver.basis().baseId(y.index(i)).isSPxRowId());
4440  rowIdx = _solver.basis().baseId(y.index(i)).getIdx();
4441  scaleExp = _scaler->getRowScaleExp(rowIdx);
4442  y.setValue(i, y.value(i) * spxLdexp(1.0, scaleExp));
4443  }
4444  }
4445  else
4446  {
4447  _solver.basis().coSolve(y, rhs);
4448  }
4449  }
4450  catch( const SPxException& E )
4451  {
4452  MSG_INFO1( spxout, spxout << "Caught exception <" << E.what() << "> while computing basis inverse row.\n" );
4453  return false;
4454  }
4455 
4456  // initialize result vector x as zero
4457  memset(coef, 0, (unsigned int)numRowsReal() * sizeof(Real));
4458 
4459  // add nonzero entries
4460  for( int i = 0; i < numColsReal(); ++i )
4461  {
4462  SPxId id = _solver.basis().baseId(i);
4463 
4464  if( id.isSPxRowId() )
4465  {
4466  assert(_solver.number(id) >= 0);
4467  assert(_solver.number(id) < numRowsReal());
4468  assert(bind[c] >= 0 || _solver.number(id) != index);
4469 
4470  coef[_solver.number(id)] = y[i];
4471  }
4472  }
4473 
4474  // if c corresponds to a row vector, we have to add a 1 at position c
4475  if( bind[c] < 0 )
4476  {
4477  assert(coef[index] == 0.0);
4478  coef[index] = 1.0;
4479  }
4480 
4481  // @todo implement returning of sparsity information like in column wise case
4482  if( ninds != NULL)
4483  *ninds = -1;
4484 
4485  // free memory
4486  spx_free(bind);
4487  }
4488 
4489  return true;
4490  }
4491 
4492 
4493 
4494  /// computes dense solution of basis matrix B * sol = rhs; returns true on success
4495  bool SoPlex::getBasisInverseTimesVecReal(Real* rhs, Real* sol, bool unscale)
4496  {
4497  VectorReal v(numRowsReal(), rhs);
4498  VectorReal x(numRowsReal(), sol);
4499 
4500  if( !hasBasis() )
4501  return false;
4502 
4504 
4505  if( !_isRealLPLoaded )
4506  return false;
4507 
4508  // we need to distinguish between column and row representation; ask the solver itself which representation it
4509  // has, since the REPRESENTATION parameter of this class might be set to automatic; in the column case we can use
4510  // the existing factorization
4511  if( _solver.rep() == SPxSolver::COLUMN )
4512  {
4513  // solve system "x = B^-1 * v"
4514  try
4515  {
4516  /* unscaling required? */
4517  if( unscale && _solver.isScaled())
4518  {
4519  /* for information on the unscaling procedure see spxscaler.h */
4520  int scaleExp;
4521  int idx;
4522 
4523  for( int i = 0; i < v.dim(); ++i)
4524  {
4525  if( isNotZero(v[i]) )
4526  {
4527  scaleExp =_scaler->getRowScaleExp(i);
4528  v[i] = spxLdexp(v[i], scaleExp);
4529  }
4530  }
4531 
4532  _solver.basis().solve(x, v);
4533 
4534  for( int i = 0; i < x.dim(); i++ )
4535  {
4536  if( isNotZero(x[i]) )
4537  {
4538  idx = _solver.number(_solver.basis().baseId(i));
4539  if( _solver.basis().baseId(i).isSPxColId() )
4540  scaleExp = _scaler->getColScaleExp(idx);
4541  else
4542  scaleExp = - _scaler->getRowScaleExp(idx);
4543  x[i] = spxLdexp(x[i], scaleExp);
4544  }
4545  }
4546  }
4547  else
4548  {
4549  _solver.basis().solve(x, v);
4550  }
4551  }
4552  catch( const SPxException& E )
4553  {
4554  MSG_INFO1( spxout, spxout << "Caught exception <" << E.what() << "> while solving with basis matrix.\n" );
4555  return false;
4556  }
4557  }
4558  else
4559  {
4560  assert(_solver.rep() == SPxSolver::ROW);
4561 
4562  DSVectorReal rowrhs(numColsReal());
4564  int* bind = 0;
4565 
4566  bool adaptScaling = unscale && _realLP->isScaled();
4567  int scaleExp;
4568  int idx;
4569 
4570  // get ordering of column basis matrix
4571  spx_alloc(bind, numRowsReal());
4572  getBasisInd(bind);
4573 
4574  // fill right-hand side for row-based system
4575  for( int i = 0; i < numColsReal(); ++i )
4576  {
4577  SPxId id = _solver.basis().baseId(i);
4578 
4579  if( id.isSPxRowId() )
4580  {
4581  assert(_solver.number(id) >= 0);
4582  assert(_solver.number(id) < numRowsReal());
4583 
4584  if( adaptScaling )
4585  {
4586  idx = _solver.number(id);
4587  scaleExp = _scaler->getRowScaleExp(idx);
4588  rowrhs.add(i, spxLdexp(v[idx], scaleExp));
4589  }
4590  else
4591  rowrhs.add(i, v[_solver.number(id)]);
4592  }
4593  else
4594  {
4595  assert(rowrhs[i] == 0.0);
4596  }
4597  }
4598 
4599  // solve system "B y = rowrhs", where B is the row basis matrix
4600  try
4601  {
4602  _solver.basis().coSolve(y, rowrhs);
4603  }
4604  catch( const SPxException& E )
4605  {
4606  MSG_INFO1( spxout, spxout << "Caught exception <" << E.what() << "> while solving with basis matrix.\n" );
4607  return false;
4608  }
4609 
4610  // fill result w.r.t. order given by bind
4611  for( int i = 0; i < numRowsReal(); ++i )
4612  {
4613  int index;
4614 
4615  index = bind[i];
4616 
4617  if( index < 0 )
4618  {
4619  index = -index-1;
4620 
4621  // should be a valid row index and in the column basis matrix, i.e., not basic w.r.t. row representation
4622  assert(index >= 0);
4623  assert(index < numRowsReal());
4624  assert(!_solver.isRowBasic(index));
4625 
4626  x[i] = v[index] - (rowVectorRealInternal(index) * Vector(numColsReal(), y.get_ptr()));
4627 
4628  if( adaptScaling )
4629  {
4630  scaleExp = -_scaler->getRowScaleExp(index);
4631  x[i] = spxLdexp(x[i], scaleExp);
4632  }
4633  }
4634  else
4635  {
4636  // should be a valid column index and in the column basis matrix, i.e., not basic w.r.t. row representation
4637  assert(index >= 0);
4638  assert(index < numColsReal());
4639  assert(!_solver.isColBasic(index));
4640 
4641  if( adaptScaling )
4642  {
4643  scaleExp = _scaler->getColScaleExp(index);
4644  x[i] = spxLdexp(y[index], scaleExp);
4645  }
4646  else
4647  x[i] = y[index];
4648  }
4649  }
4650 
4651  // free memory
4652  spx_free(bind);
4653  }
4654  return true;
4655  }
4656 
4657 
4658 
4659  /// multiply with basis matrix; B * vec (inplace)
4660  bool SoPlex::multBasis(Real* vec, bool unscale)
4661  {
4662  if( !hasBasis() )
4663  return false;
4664 
4666 
4667  if( !_isRealLPLoaded )
4668  return false;
4669 
4670  if( _solver.rep() == SPxSolver::COLUMN )
4671  {
4672  int basisdim = numRowsReal();
4673 
4674  // create Vector from input values
4675  Vector x(basisdim, vec);
4676 
4677  if( unscale && _solver.isScaled() )
4678  {
4679  /* for information on the unscaling procedure see spxscaler.h */
4680 
4681  int scaleExp;
4682  for( int i = 0; i < basisdim; ++i)
4683  {
4684  if( isNotZero(vec[i]) )
4685  {
4686  if( _solver.basis().baseId(i).isSPxColId() )
4687  scaleExp = - _scaler->getColScaleExp(_solver.number(_solver.basis().baseId(i)));
4688  else
4690 
4691  vec[i] = spxLdexp(vec[i], scaleExp);
4692  }
4693  }
4694  _solver.basis().multBaseWith(x);
4695  for( int i = 0; i < basisdim; ++i)
4696  {
4697  scaleExp = _scaler->getRowScaleExp(i);
4698  vec[i] = spxLdexp(vec[i], -scaleExp);
4699  }
4700  }
4701  else
4702  _solver.basis().multBaseWith(x);
4703  }
4704  else
4705  {
4706  int colbasisdim = numRowsReal();
4707 
4708  DSVector y(colbasisdim);
4709 
4710  y.clear();
4711 
4712  // create Vector from input values
4713  Vector x(colbasisdim, vec);
4714 
4715  int* bind = 0;
4716  int index;
4717 
4718  // get ordering of column basis matrix
4719  spx_alloc(bind, colbasisdim);
4720  getBasisInd(bind);
4721 
4722  // temporarily create the column basis and multiply every column with x
4723  for( int i = 0; i < colbasisdim; ++i)
4724  {
4725  if( isNotZero(x[i]) )
4726  {
4727  // get vector corresponding to requested index i
4728  index = bind[i];
4729  // r corresponds to a row vector
4730  if( index < 0 )
4731  {
4732  // transform index to actual row index
4733  index = -index - 1;
4734 
4735  // should be a valid row index and in the column basis matrix, i.e., not basic w.r.t. row representation
4736  assert(index >= 0);
4737  assert(index < numRowsReal());
4738  assert(!_solver.isRowBasic(index));
4739 
4740  y.add(x[i] * UnitVectorReal(index));
4741  }
4742  // r corresponds to a column vector
4743  else
4744  {
4745  // should be a valid column index and in the column basis matrix, i.e., not basic w.r.t. row representation
4746  assert(index < numColsReal());
4747  assert(!_solver.isColBasic(index));
4748 
4749  if( unscale && _solver.isScaled() )
4750  {
4751  DSVector col;
4752  _solver.getColVectorUnscaled(index, col);
4753  y.add(x[i] * col);
4754  }
4755 
4756  y.add(x[i] * _solver.colVector(index));
4757  }
4758  }
4759  }
4760  spx_free(bind);
4761  x = y;
4762  }
4763 
4764  return true;
4765  }
4766 
4767 
4768 
4769  /// multiply with transpose of basis matrix; vec * B^T (inplace)
4770  bool SoPlex::multBasisTranspose(Real* vec, bool unscale)
4771  {
4772  if( !hasBasis() )
4773  return false;
4774 
4776 
4777  if( !_isRealLPLoaded )
4778  return false;
4779 
4780  if( _solver.rep() == SPxSolver::COLUMN )
4781  {
4782  int basisdim = numRowsReal();
4783 
4784  // create Vector from input values
4785  Vector x(basisdim, vec);
4786 
4787  if( unscale && _solver.isScaled() )
4788  {
4789  /* for information on the unscaling procedure see spxscaler.h */
4790 
4791  int scaleExp;
4792  for( int i = 0; i < basisdim; ++i)
4793  {
4794  if( isNotZero(vec[i]) )
4795  {
4796  scaleExp = - _scaler->getRowScaleExp(i);
4797  vec[i] = spxLdexp(vec[i], scaleExp);
4798  }
4799  }
4800  _solver.basis().multWithBase(x);
4801  for( int i = 0; i < basisdim; ++i)
4802  {
4803  if( isNotZero(vec[i]) )
4804  {
4805  if( _solver.basis().baseId(i).isSPxColId() )
4806  scaleExp = - _scaler->getColScaleExp(_solver.number(_solver.basis().baseId(i)));
4807  else
4809 
4810  vec[i] = spxLdexp(vec[i], scaleExp);
4811  }
4812  }
4813  }
4814  else
4815  _solver.basis().multWithBase(x);
4816  }
4817  else
4818  {
4819  int colbasisdim = numRowsReal();
4820 
4821  DSVector y(colbasisdim);
4822 
4823  // create Vector from input values
4824  Vector x(colbasisdim, vec);
4825 
4826  int* bind = 0;
4827  int index;
4828 
4829  // get ordering of column basis matrix
4830  spx_alloc(bind, colbasisdim);
4831  getBasisInd(bind);
4832 
4833  // temporarily create the column basis and multiply every column with x
4834  for( int i = 0; i < colbasisdim; ++i)
4835  {
4836  // get vector corresponding to requested index i
4837  index = bind[i];
4838  // r corresponds to a row vector
4839  if( index < 0 )
4840  {
4841  // transform index to actual row index
4842  index = -index - 1;
4843 
4844  // should be a valid row index and in the column basis matrix, i.e., not basic w.r.t. row representation
4845  assert(index >= 0);
4846  assert(index < numRowsReal());
4847  assert(!_solver.isRowBasic(index));
4848 
4849  y.add(i, x * UnitVectorReal(index));
4850  }
4851  // r corresponds to a column vector
4852  else
4853  {
4854  // should be a valid column index and in the column basis matrix, i.e., not basic w.r.t. row representation
4855  assert(index < numColsReal());
4856  assert(!_solver.isColBasic(index));
4857 
4858  if( unscale && _solver.isScaled() )
4859  {
4860  DSVector col;
4861  _solver.getColVectorUnscaled(index, col);
4862  y.add(i, x * col);
4863  }
4864  else
4865  y.add(i, x * _solver.colVector(index));
4866  }
4867  }
4868  spx_free(bind);
4869  x = y;
4870  }
4871 
4872  return true;
4873  }
4874 
4875 
4876 
4877  /// compute rational basis inverse; returns true on success
4879  {
4880  if( !hasBasis() )
4881  {
4884  return false;
4885  }
4886 
4889  {
4893  }
4894 
4896  return true;
4897 
4898  return false;
4899  }
4900 
4901 
4902 
4903  /// gets an array of indices for the columns of the rational basis matrix; bind[i] >= 0 means that the i-th column of
4904  /// the basis matrix contains variable bind[i]; bind[i] < 0 means that the i-th column of the basis matrix contains
4905  /// the slack variable for row -bind[i]-1; performs rational factorization if not available; returns true on success
4907  {
4910 
4912  return false;
4913 
4914  bind = _rationalLUSolverBind;
4915  assert(bind.size() == numRowsRational());
4916  return true;
4917  }
4918 
4919 
4920 
4921  /// computes row r of basis inverse; performs rational factorization if not available; returns true on success
4923  {
4926 
4928  return false;
4929 
4930  try
4931  {
4932  vec.reDim(numRowsRational());
4934  }
4935  catch( const SPxException& E )
4936  {
4937  MSG_INFO1( spxout, spxout << "Caught exception <" << E.what() << "> while computing rational basis inverse row.\n" );
4938  return false;
4939  }
4940  return true;
4941  }
4942 
4943 
4944 
4945  /// computes column c of basis inverse; performs rational factorization if not available; returns true on success
4947  {
4950 
4952  return false;
4953 
4954  try
4955  {
4956  vec.reDim(numRowsRational());
4958  }
4959  catch( const SPxException& E )
4960  {
4961  MSG_INFO1( spxout, spxout << "Caught exception <" << E.what() << "> while computing rational basis inverse column.\n" );
4962  return false;
4963  }
4964  return true;
4965  }
4966 
4967 
4968 
4969  /// computes solution of basis matrix B * sol = rhs; performs rational factorization if not available; returns true
4970  /// on success
4972  {
4975 
4977  return false;
4978 
4979  try
4980  {
4981  sol.reDim(numRowsRational());
4982  _rationalLUSolver.solveRight(sol, rhs);
4983  }
4984  catch( const SPxException& E )
4985  {
4986  MSG_INFO1( spxout, spxout << "Caught exception <" << E.what() << "> during right solve with rational basis inverse.\n" );
4987  return false;
4988  }
4989  return true;
4990  }
4991 
4992 
4993 
4994  /// sets starting basis via arrays of statuses
4996  {
4998 
4999  if( _isRealLPLoaded )
5000  {
5001  assert(numRowsReal() == _solver.nRows());
5002  assert(numColsReal() == _solver.nCols());
5003 
5004  _solver.setBasis(rows, cols);
5006  }
5007  else
5008  {
5011 
5012  for( int i = numRowsReal() - 1; i >= 0; i-- )
5013  _basisStatusRows[i] = rows[i];
5014 
5015  for( int j = numColsReal() - 1; j >= 0; j-- )
5016  _basisStatusCols[j] = cols[j];
5017 
5018  _hasBasis = true;
5019  }
5020  }
5021 
5022 
5023 
5024  /// clears starting basis
5026  {
5027  _solver.reLoad();
5028  _status = _solver.status();
5029  _hasBasis = false;
5031  }
5032 
5033 
5034 
5035  /// number of iterations since last call to solve
5037  {
5038  return _statistics->iterations;
5039  }
5040 
5041 
5042 
5043  /// time spent in last call to solve
5045  {
5046  return _statistics->solvingTime->time();
5047  }
5048 
5049 
5050 
5051  /// statistical information in form of a string
5052  std::string SoPlex::statisticString() const
5053  {
5054  std::stringstream s;
5055  s << "Factorizations : " << std::setw(10) << _statistics->luFactorizationsReal << std::endl
5056  << " Time spent : " << std::setw(10) << std::fixed << std::setprecision(2) << _statistics->luFactorizationTimeReal << std::endl
5057  << "Solves : " << std::setw(10) << _statistics->luSolvesReal << std::endl
5058  << " Time spent : " << std::setw(10) << _statistics->luSolveTimeReal << std::endl
5059  << "Solution time : " << std::setw(10) << std::fixed << std::setprecision(2) << solveTime() << std::endl
5060  << "Iterations : " << std::setw(10) << numIterations() << std::endl;
5061 
5062  return s.str();
5063  }
5064 
5065 
5066 
5067  /// name of starter
5069  {
5070  if( _starter )
5071  return _starter->getName();
5072  else
5073  return "none";
5074  }
5075 
5076 
5077 
5078  /// name of simplifier
5080  {
5081  if( _simplifier )
5082  return _simplifier->getName();
5083  else
5084  return "none";
5085  }
5086 
5087 
5088 
5089  /// name of scaling method after simplifier
5091  {
5092  if( _scaler )
5093  return _scaler->getName();
5094  else
5095  return "none";
5096  }
5097 
5098 
5099 
5100  /// name of currently loaded pricer
5102  {
5103  return _solver.pricer()->getName();
5104  }
5105 
5106 
5107 
5108  /// name of currently loaded ratiotester
5110  {
5111  return _solver.ratiotester()->getName();
5112  }
5113 
5114 
5115 
5116  /// reads LP file in LP or MPS format according to READMODE parameter; gets row names, column names, and
5117  /// integer variables if desired; returns true on success
5118  bool SoPlex::readFile(const char* filename, NameSet* rowNames, NameSet* colNames, DIdxSet* intVars)
5119  {
5120  bool success = false;
5122  success = _readFileReal(filename, rowNames, colNames, intVars);
5123  else
5124  success = _readFileRational(filename, rowNames, colNames, intVars);
5125 
5126  // storing the row and column names for use in the DBDS print basis methods
5127  _rowNames = rowNames;
5128  _colNames = colNames;
5129 
5130  return success;
5131  }
5132 
5133  /// writes real LP to file; LP or MPS format is chosen from the extension in \p filename; if \p rowNames and \p
5134  /// colNames are \c NULL, default names are used; if \p intVars is not \c NULL, the variables contained in it are
5135  /// marked as integer; returns true on success
5136  bool SoPlex::writeFileReal(const char* filename, const NameSet* rowNames, const NameSet* colNames, const DIdxSet* intVars, const bool unscale) const
5137  {
5138  ///@todo implement return value
5139  if( unscale && _realLP->isScaled() )
5140  {
5141  MSG_INFO3( spxout, spxout << "copy LP to write unscaled original problem" << std::endl; )
5142  SPxLPReal* origLP;
5143  origLP = 0;
5144  spx_alloc(origLP);
5145  origLP = new (origLP) SPxLPReal(*_realLP);
5146  origLP->unscaleLP();
5147  origLP->writeFile(filename, rowNames, colNames, intVars);
5148  origLP->~SPxLPReal();
5149  spx_free(origLP);
5150  }
5151  else
5152  _realLP->writeFile(filename, rowNames, colNames, intVars);
5153 
5154  return true;
5155  }
5156 
5157 
5158 
5159  /// writes rational LP to file; LP or MPS format is chosen from the extension in \p filename; if \p rowNames and \p
5160  /// colNames are \c NULL, default names are used; if \p intVars is not \c NULL, the variables contained in it are
5161  /// marked as integer; returns true on success
5162  bool SoPlex::writeFileRational(const char* filename, const NameSet* rowNames, const NameSet* colNames, const DIdxSet* intVars) const
5163  {
5165  return false;
5166  else
5167  {
5168  assert(_rationalLP != 0);
5169  _rationalLP->writeFile(filename, rowNames, colNames, intVars);
5170 
5171  ///@todo implement return value
5172  return true;
5173  }
5174  }
5175 
5176 
5177 
5178  /// writes the dual of the real LP to file; LP or MPS format is chosen from the extension in \p filename;
5179  /// if \p rowNames and \p colNames are \c NULL, default names are used; if \p intVars is not \c NULL,
5180  /// the variables contained in it are marked as integer; returns true on success
5181  bool SoPlex::writeDualFileReal(const char* filename, const NameSet* rowNames, const NameSet* colNames, const DIdxSet* intVars) const
5182  {
5183  SPxLPReal dualLP;
5184  _realLP->buildDualProblem(dualLP);
5185  dualLP.setOutstream(spxout);
5186 
5187  // swap colnames and rownames
5188  dualLP.writeFile(filename, colNames, rowNames);
5189  return true;
5190  }
5191 
5192 
5193 
5194  /// reads basis information from \p filename and returns true on success; if \p rowNames and \p colNames are \c NULL,
5195  /// default names are assumed; returns true on success
5196  bool SoPlex::readBasisFile(const char* filename, const NameSet* rowNames, const NameSet* colNames)
5197  {
5198  clearBasis();
5199 
5200 #if 1
5201  assert(filename != 0);
5202  assert(_realLP != 0);
5203 
5204  // start timing
5206 
5207  // read
5208  if( !_isRealLPLoaded )
5209  {
5210  assert(_realLP != &_solver);
5211 
5213  _realLP->~SPxLPReal();
5214  spx_free(_realLP);
5215  _realLP = &_solver;
5216  _isRealLPLoaded = true;
5217  }
5218  _hasBasis = _solver.readBasisFile(filename, rowNames, colNames);
5219  assert(_hasBasis == (_solver.basis().status() > SPxBasis::NO_PROBLEM));
5220 
5221  // stop timing
5223 
5224  return _hasBasis;
5225 #else
5226  // this is alternative code for reading bases without the SPxSolver class
5227  assert(filename != 0);
5228 
5229  // start timing
5231 
5232  // read
5233  spxifstream file(filename);
5234 
5235  if( !file )
5236  return false;
5237 
5238  // get problem size
5239  int numRows = numRowsReal();
5240  int numCols = numColsReal();
5241 
5242  // prepare column names
5243  const NameSet* colNamesPtr = colNames;
5244  NameSet* tmpColNames = 0;
5245  if( colNames == 0 )
5246  {
5247  std::stringstream name;
5248 
5249  spx_alloc(tmpColNames);
5250  tmpColNames = new (tmpColNames) NameSet();
5251  tmpColNames->reMax(numCols);
5252 
5253  for( int j = 0; j < numCols; ++j )
5254  {
5255  name << "x" << j;
5256  tmpColNames->add(name.str().c_str());
5257  }
5258 
5259  colNamesPtr = tmpColNames;
5260  }
5261 
5262  // prepare row names
5263  const NameSet* rowNamesPtr = rowNames;
5264  NameSet* tmpRowNames = 0;
5265  if( rowNamesPtr == 0 )
5266  {
5267  std::stringstream name;
5268 
5269  spx_alloc(tmpRowNames);
5270  tmpRowNames = new (tmpRowNames) NameSet();
5271  tmpRowNames->reMax(numRows);
5272 
5273  for( int i = 0; i < numRows; ++i )
5274  {
5275  name << "C" << i;
5276  tmpRowNames->add(name.str().c_str());
5277  }
5278 
5279  rowNamesPtr = tmpRowNames;
5280  }
5281 
5282  // initialize with default slack basis
5283  _basisStatusRows.reSize(numRows);
5284  _basisStatusCols.reSize(numCols);
5285 
5286  for( int i = 0; i < numRows; i++ )
5288 
5289  for( int i = 0; i < numCols; i++ )
5290  {
5291  if( lowerRealInternal(i) == upperRealInternal(i) )
5293  else if( lowerRealInternal(i) <= double(-realParam(SoPlex::INFTY)) && upperRealInternal(i) >= double(realParam(SoPlex::INFTY)) )
5295  else if( lowerRealInternal(i) <= double(-realParam(SoPlex::INFTY)) )
5297  else
5299  }
5300 
5301  // read basis
5302  MPSInput mps(file);
5303  if( mps.readLine() && (mps.field0() != 0) && !strcmp(mps.field0(), "NAME") )
5304  {
5305  while( mps.readLine() )
5306  {
5307  int c = -1;
5308  int r = -1;
5309 
5310  if( mps.field0() != 0 && !strcmp(mps.field0(), "ENDATA") )
5311  {
5313  break;
5314  }
5315 
5316  if( mps.field1() == 0 || mps.field2() == 0 )
5317  break;
5318 
5319  if( (c = colNamesPtr->number(mps.field2())) < 0 )
5320  break;
5321 
5322  if( *mps.field1() == 'X' )
5323  {
5324  if( mps.field3() == 0 || (r = rowNamesPtr->number(mps.field3())) < 0 )
5325  break;
5326  }
5327 
5328  if( !strcmp(mps.field1(), "XU") )
5329  {
5333  else if( _rowTypes[r] == SoPlex::RANGETYPE_FIXED )
5335  else
5337  }
5338  else if( !strcmp(mps.field1(), "XL") )
5339  {
5343  else if( _rowTypes[r] == SoPlex::RANGETYPE_FIXED )
5345  else
5347  }
5348  else if( !strcmp(mps.field1(), "UL") )
5349  {
5351  }
5352  else if( !strcmp(mps.field1(), "LL") )
5353  {
5355  }
5356  else
5357  {
5358  mps.syntaxError();
5359  break;
5360  }
5361  }
5362  }
5363 
5364  if( rowNames == 0 )
5365  {
5366  tmpRowNames->~NameSet();
5367  spx_free(tmpRowNames);
5368  }
5369 
5370  if( colNames == 0 )
5371  {
5372  tmpColNames->~NameSet();
5373  spx_free(tmpColNames);
5374  }
5375 
5376  _hasBasis = !mps.hasError();
5377 
5378  // stop timing
5380 
5381  return _hasBasis;
5382 #endif
5383  }
5384 
5385 
5386 
5387  /// writes basis information to \p filename; if \p rowNames and \p colNames are \c NULL, default names are used;
5388  /// returns true on success
5389  bool SoPlex::writeBasisFile(const char* filename, const NameSet* rowNames, const NameSet* colNames, const bool cpxFormat) const
5390  {
5391  assert(filename != 0);
5392 
5393  if( _isRealLPLoaded )
5394  return _solver.writeBasisFile(filename, rowNames, colNames, cpxFormat);
5395  else
5396  {
5397  std::ofstream file(filename);
5398  if( !file.good() )
5399  return false;
5400 
5401  file.setf(std::ios::left);
5402  file << "NAME " << filename << "\n";
5403 
5404  // do not write basis if there is none
5405  if( !_hasBasis )
5406  {
5407  file << "ENDATA\n";
5408  return true;
5409  }
5410 
5411  // start writing
5412  int numRows = _basisStatusRows.size();
5413  int numCols = _basisStatusCols.size();
5414  int row = 0;
5415 
5416  for( int col = 0; col < numCols; col++ )
5417  {
5418  assert(_basisStatusCols[col] != SPxSolver::UNDEFINED);
5419 
5420  if( _basisStatusCols[col] == SPxSolver::BASIC )
5421  {
5422  // find nonbasic row
5423  for( ; row < numRows; row++ )
5424  {
5425  assert(_basisStatusRows[row] != SPxSolver::UNDEFINED);
5426  if( _basisStatusRows[row] != SPxSolver::BASIC )
5427  break;
5428  }
5429 
5430  assert(row != numRows);
5431 
5432  if( _basisStatusRows[row] == SPxSolver::ON_UPPER && (!cpxFormat || _rowTypes[row] == SoPlex::RANGETYPE_BOXED) )
5433  file << " XU ";
5434  else
5435  file << " XL ";
5436 
5437  file << std::setw(8);
5438  if( colNames != 0 && colNames->has(col) )
5439  file << (*colNames)[col];
5440  else
5441  file << "x" << col;
5442 
5443  file << " ";
5444  if( rowNames != 0 && rowNames->has(row) )
5445  file << (*rowNames)[row];
5446  else
5447  file << "C" << row;
5448 
5449  file << "\n";
5450  row++;
5451  }
5452  else
5453  {
5455  {
5456  file << " UL ";
5457 
5458  file << std::setw(8);
5459  if( colNames != 0 && colNames->has(col) )
5460  file << (*colNames)[col];
5461  else
5462  file << "x" << col;
5463 
5464  file << "\n";
5465  }
5466  }
5467  }
5468 
5469  file << "ENDATA\n";
5470 
5471 #ifndef NDEBUG
5472  // check that the remaining rows are basic
5473  for( ; row < numRows; row++ )
5474  {
5475  assert(_basisStatusRows[row] == SPxSolver::BASIC);
5476  }
5477 #endif
5478 
5479  return true;
5480  }
5481  }
5482 
5483 
5484 
5485  /// writes internal LP, basis information, and parameter settings; if \p rowNames and \p colNames are \c NULL,
5486  /// default names are used
5487  void SoPlex::writeStateReal(const char* filename, const NameSet* rowNames, const NameSet* colNames, const bool cpxFormat) const
5488  {
5489  std::string ofname;
5490 
5491  // write parameter settings
5492  ofname = std::string(filename) + ".set";
5493  saveSettingsFile(ofname.c_str());
5494 
5495  // write problem in MPS/LP format
5496  ofname = std::string(filename) + ((cpxFormat) ? ".lp" : ".mps");
5497  writeFileReal(ofname.c_str(), rowNames, colNames, 0);
5498 
5499  // write basis
5500  ofname = std::string(filename) + ".bas";
5501  writeBasisFile(ofname.c_str(), rowNames, colNames, cpxFormat);
5502  }
5503 
5504 
5505 
5506  /// writes internal LP, basis information, and parameter settings; if \p rowNames and \p colNames are \c NULL,
5507  /// default names are used
5508  void SoPlex::writeStateRational(const char* filename, const NameSet* rowNames, const NameSet* colNames, const bool cpxFormat) const
5509  {
5510  std::string ofname;
5511 
5512  // write parameter settings
5513  ofname = std::string(filename) + ".set";
5514  saveSettingsFile(ofname.c_str());
5515 
5516  // write problem in MPS/LP format
5517  ofname = std::string(filename) + ((cpxFormat) ? ".lp" : ".mps");
5518  writeFileRational(ofname.c_str(), rowNames, colNames, 0);
5519 
5520  // write basis
5521  ofname = std::string(filename) + ".bas";
5522  writeBasisFile(ofname.c_str(), rowNames, colNames, cpxFormat);
5523  }
5524 
5525 
5526 
5527  /// returns boolean parameter value
5528  bool SoPlex::boolParam(const BoolParam param) const
5529  {
5530  assert(param >= 0);
5531  assert(param < SoPlex::BOOLPARAM_COUNT);
5532  return _currentSettings->_boolParamValues[param];
5533  }
5534 
5535 
5536 
5537  /// returns integer parameter value
5538  int SoPlex::intParam(const IntParam param) const
5539  {
5540  assert(param >= 0);
5541  assert(param < INTPARAM_COUNT);
5542  return _currentSettings->_intParamValues[param];
5543  }
5544 
5545 
5546 
5547  /// returns real parameter value
5548  Real SoPlex::realParam(const RealParam param) const
5549  {
5550  assert(param >= 0);
5551  assert(param < REALPARAM_COUNT);
5552  return _currentSettings->_realParamValues[param];
5553  }
5554 
5555 
5556 
5557 #ifdef SOPLEX_WITH_RATIONALPARAM
5558  /// returns rational parameter value
5559  Rational SoPlex::rationalParam(const RationalParam param) const
5560  {
5561  assert(param >= 0);
5562  assert(param < RATIONALPARAM_COUNT);
5563  return _currentSettings->_rationalParamValues[param];
5564  }
5565 #endif
5566 
5567 
5568 
5569  /// returns current parameter settings
5571  {
5572  return *_currentSettings;
5573  }
5574 
5575 
5576 
5577  /// sets boolean parameter value; returns true on success
5578  bool SoPlex::setBoolParam(const BoolParam param, const bool value, const bool init)
5579  {
5580  assert(param >= 0);
5581  assert(param < SoPlex::BOOLPARAM_COUNT);
5582  assert(init || _isConsistent());
5583 
5584  if( !init && value == boolParam(param) )
5585  return true;
5586 
5587  switch( param )
5588  {
5589  case LIFTING:
5590  break;
5591  case EQTRANS:
5592  break;
5593  case TESTDUALINF:
5594  break;
5595  case RATFAC:
5596  break;
5597  case USEDECOMPDUALSIMPLEX:
5598  break;
5599  case COMPUTEDEGEN:
5600  break;
5601  case USECOMPDUAL:
5602  break;
5603  case EXPLICITVIOL:
5604  break;
5605  case ACCEPTCYCLING:
5606  break;
5607  case RATREC:
5608  break;
5609  case POWERSCALING:
5610  break;
5611  case RATFACJUMP:
5612  break;
5613  case ROWBOUNDFLIPS:
5615  break;
5616  case PERSISTENTSCALING:
5617  break;
5618  case FULLPERTURBATION:
5620  break;
5621  default:
5622  return false;
5623  }
5624 
5625  _currentSettings->_boolParamValues[param] = value;
5626  return true;
5627  }
5628 
5629 
5630 
5631  /// sets integer parameter value; returns true on success
5632  bool SoPlex::setIntParam(const IntParam param, const int value, const bool init)
5633  {
5634  assert(param >= 0);
5635  assert(param < INTPARAM_COUNT);
5636  assert(init || _isConsistent());
5637 
5638  if( !init && value == intParam(param) )
5639  return true;
5640 
5641  // check for a valid parameter value wrt bounds
5642  if( value < _currentSettings->intParam.lower[param] || value > _currentSettings->intParam.upper[param] )
5643  return false;
5644 
5645  switch( param )
5646  {
5647  // objective sense
5648  case SoPlex::OBJSENSE:
5649  if( value != SoPlex::OBJSENSE_MAXIMIZE && value != SoPlex::OBJSENSE_MINIMIZE )
5650  return false;
5652  if( _rationalLP != 0 )
5655  break;
5656 
5657  // type of computational form, i.e., column or row representation
5660  return false;
5661  break;
5662 
5663  // type of algorithm, i.e., primal or dual
5664  case SoPlex::ALGORITHM:
5665  // decide upon entering/leaving at solve time depending on representation
5666  break;
5667 
5668  // type of LU update
5671  return false;
5673  break;
5674 
5675  // maximum number of updates before fresh factorization
5677  if( value == 0 )
5679  else
5680  _solver.basis().setMaxUpdates(value);
5681  break;
5682 
5683  // iteration limit (-1 if unlimited)
5684  case SoPlex::ITERLIMIT:
5685  break;
5686 
5687  // refinement limit (-1 if unlimited)
5688  case SoPlex::REFLIMIT:
5689  break;
5690 
5691  // stalling refinement limit (-1 if unlimited)
5692  case SoPlex::STALLREFLIMIT:
5693  break;
5694 
5695  // display frequency
5696  case SoPlex::DISPLAYFREQ:
5697  _solver.setDisplayFreq(value);
5698  break;
5699 
5700  // verbosity level
5701  case SoPlex::VERBOSITY:
5702  switch(value)
5703  {
5704  case 0:
5706  break;
5707  case 1:
5709  break;
5710  case 2:
5712  break;
5713  case 3:
5715  break;
5716  case 4:
5718  break;
5719  case 5:
5721  break;
5722  }
5723  break;
5724 
5725  // type of simplifier
5726  case SoPlex::SIMPLIFIER:
5727  switch( value )
5728  {
5729  case SIMPLIFIER_OFF:
5730  _simplifier = 0;
5731  break;
5732  case SIMPLIFIER_AUTO:
5734  assert(_simplifier != 0);
5735  break;
5736  default:
5737  return false;
5738  }
5739  break;
5740 
5741  // type of scaler
5742  case SoPlex::SCALER:
5743  switch( value )
5744  {
5745  case SCALER_OFF:
5746  _scaler = 0;
5747  break;
5748  case SCALER_UNIEQUI:
5750  break;
5751  case SCALER_BIEQUI:
5753  break;
5754  case SCALER_GEO1:
5755  _scaler = &_scalerGeo1;
5756  break;
5757  case SCALER_GEO8:
5758  _scaler = &_scalerGeo8;
5759  break;
5760  case SCALER_LEASTSQ:
5762  break;
5763  case SCALER_GEOEQUI:
5765  break;
5766  default:
5767  return false;
5768  }
5769  break;
5770 
5771  // type of starter used to create crash basis
5772  case SoPlex::STARTER:
5773  switch( value )
5774  {
5775  case STARTER_OFF:
5776  _starter = 0;
5777  break;
5778  case STARTER_WEIGHT:
5780  break;
5781  case STARTER_SUM:
5782  _starter = &_starterSum;
5783  break;
5784  case STARTER_VECTOR:
5786  break;
5787  default:
5788  return false;
5789  }
5790  break;
5791 
5792  // type of pricer
5793  case SoPlex::PRICER:
5794  switch( value )
5795  {
5796  case PRICER_AUTO:
5798  break;
5799  case PRICER_DANTZIG:
5801  break;
5802  case PRICER_PARMULT:
5804  break;
5805  case PRICER_DEVEX:
5807  break;
5808  case PRICER_QUICKSTEEP:
5810  break;
5811  case PRICER_STEEP:
5813  break;
5814  default:
5815  return false;
5816  }
5817  break;
5818 
5819  // mode for synchronizing real and rational LP
5820  case SoPlex::SYNCMODE:
5821  switch( value )
5822  {
5823  case SYNCMODE_ONLYREAL:
5824  if( _rationalLP != 0 )
5825  {
5826  _rationalLP->~SPxLPRational();
5828  }
5829  break;
5830  case SYNCMODE_AUTO:
5831  if( intParam(param) == SYNCMODE_ONLYREAL )
5832  _syncLPRational();
5833  break;
5834  case SYNCMODE_MANUAL:
5836  break;
5837  default:
5838  return false;
5839  }
5840  break;
5841 
5842  // mode for reading LP files; nothing to do but change the value if valid
5843  case SoPlex::READMODE:
5844  switch( value )
5845  {
5846  case READMODE_REAL:
5847  case READMODE_RATIONAL:
5848  break;
5849  default:
5850  return false;
5851  }
5852  break;
5853 
5854  // mode for iterative refinement strategy; nothing to do but change the value if valid
5855  case SoPlex::SOLVEMODE:
5856  switch( value )
5857  {
5858  case SOLVEMODE_REAL:
5859  case SOLVEMODE_AUTO:
5860  case SOLVEMODE_RATIONAL:
5861  break;
5862  default:
5863  return false;
5864  }
5865  break;
5866 
5867  // mode for a posteriori feasibility checks; nothing to do but change the value if valid
5868  case SoPlex::CHECKMODE:
5869  switch( value )
5870  {
5871  case CHECKMODE_REAL:
5872  case CHECKMODE_AUTO:
5873  case CHECKMODE_RATIONAL:
5874  break;
5875  default:
5876  return false;
5877  }
5878  break;
5879 
5880  // type of ratio test
5881  case SoPlex::RATIOTESTER:
5882  switch( value )
5883  {
5884  case RATIOTESTER_TEXTBOOK:
5886  break;
5887  case RATIOTESTER_HARRIS:
5889  break;
5890  case RATIOTESTER_FAST:
5892  break;
5895  break;
5896  default:
5897  return false;
5898  }
5899  break;
5900 
5901  // type of timer
5902  case SoPlex::TIMER:
5903  switch( value )
5904  {
5905  case TIMER_OFF:
5907  break;
5908  case TIMER_CPU:
5910  break;
5911  case TIMER_WALLCLOCK:
5913  break;
5914  default:
5915  return false;
5916  }
5917  break;
5918 
5919  // mode of hyper pricing
5920  case SoPlex::HYPER_PRICING:
5921  switch( value )
5922  {
5923  case HYPER_PRICING_OFF:
5924  case HYPER_PRICING_AUTO:
5925  case HYPER_PRICING_ON:
5926  break;
5927  default:
5928  return false;
5929  }
5930  break;
5931 
5932  // minimum number of stalling refinements since last pivot to trigger rational factorization
5934  break;
5935 
5936  // maximum number of conjugate gradient iterations in least square scaling
5938  if( _scaler )
5939  _scaler->setIntParam(value);
5940  break;
5941 
5942  // mode of solution polishing
5944  switch( value )
5945  {
5946  case POLISHING_OFF:
5948  break;
5949  case POLISHING_INTEGRALITY:
5951  break;
5954  break;
5955  default:
5956  return false;
5957  }
5958  break;
5959 
5960  // the decomposition based simplex parameter settings
5961  case DECOMP_ITERLIMIT:
5962  break;
5963  case DECOMP_MAXADDEDROWS:
5964  break;
5965  case DECOMP_DISPLAYFREQ:
5966  break;
5967  case DECOMP_VERBOSITY:
5968  break;
5969 
5970  // printing of condition n
5971  case PRINTCONDITION:
5973  break;
5974 
5975  default:
5976  return false;
5977  }
5978 
5979  _currentSettings->_intParamValues[param] = value;
5980  return true;
5981  }
5982 
5983 
5984 
5985  /// sets real parameter value; returns true on success
5986  bool SoPlex::setRealParam(const RealParam param, const Real value, const bool init)
5987  {
5988  assert(param >= 0);
5989  assert(param < REALPARAM_COUNT);
5990  assert(init || _isConsistent());
5991 
5992  if( !init && value == realParam(param) )
5993  return true;
5994 
5995  if( value < _currentSettings->realParam.lower[param] || value > _currentSettings->realParam.upper[param] )
5996  return false;
5997 
5998  // required to set a different feastol or opttol
5999  Real tmp_value = value;
6000 
6001  switch( param )
6002  {
6003  // primal feasibility tolerance; passed to the floating point solver only when calling solve()
6004  case SoPlex::FEASTOL:
6005 #ifndef SOPLEX_WITH_GMP
6006  if( value < DEFAULT_EPS_PIVOT )
6007  {
6008  MSG_WARNING( spxout, spxout << "Cannot set feasibility tolerance to small value " << value << " without GMP - using " << DEFAULT_EPS_PIVOT << ".\n");
6009  tmp_value = DEFAULT_EPS_PIVOT;
6011  break;
6012  }
6013 #endif
6014  _rationalFeastol = value;
6015  break;
6016 
6017  // dual feasibility tolerance; passed to the floating point solver only when calling solve()
6018  case SoPlex::OPTTOL:
6019 #ifndef SOPLEX_WITH_GMP
6020  if( value < DEFAULT_EPS_PIVOT )
6021  {
6022  MSG_WARNING( spxout, spxout << "Cannot set optimality tolerance to small value " << value << " without GMP - using " << DEFAULT_EPS_PIVOT << ".\n");
6023  tmp_value = DEFAULT_EPS_PIVOT;
6025  break;
6026  }
6027 #endif
6028  _rationalOpttol = value;
6029  break;
6030 
6031  // general zero tolerance
6032  case SoPlex::EPSILON_ZERO:
6033  Param::setEpsilon(value);
6034  break;
6035 
6036  // zero tolerance used in factorization
6039  break;
6040 
6041  // zero tolerance used in update of the factorization
6043  Param::setEpsilonUpdate(value);
6044  break;
6045 
6046  // pivot zero tolerance used in factorization (declare numerical singularity for small LU pivots)
6047  case SoPlex::EPSILON_PIVOT:
6048  Param::setEpsilonPivot(value);
6049  break;
6050 
6051  // infinity threshold
6052  case SoPlex::INFTY:
6053  _rationalPosInfty = value;
6054  _rationalNegInfty = -value;
6057  break;
6058 
6059  // time limit in seconds (INFTY if unlimited)
6060  case SoPlex::TIMELIMIT:
6061  break;
6062 
6063  // lower limit on objective value is set in solveReal()
6065  break;
6066 
6067  // upper limit on objective value is set in solveReal()
6069  break;
6070 
6071  // working tolerance for feasibility in floating-point solver
6072  case SoPlex::FPFEASTOL:
6073  break;
6074 
6075  // working tolerance for optimality in floating-point solver
6076  case SoPlex::FPOPTTOL:
6077  break;
6078 
6079  // maximum increase of scaling factors between refinements
6080  case SoPlex::MAXSCALEINCR:
6081  _rationalMaxscaleincr = value;
6082  break;
6083 
6084  // lower threshold in lifting (nonzero matrix coefficients with smaller absolute value will be reformulated)
6085  case SoPlex::LIFTMINVAL:
6086  break;
6087 
6088  // upper threshold in lifting (nonzero matrix coefficients with larger absolute value will be reformulated)
6089  case SoPlex::LIFTMAXVAL:
6090  break;
6091 
6092  // threshold for sparse pricing
6094  break;
6095 
6096  // threshold on number of rows vs. number of columns for switching from column to row representations in auto mode
6098  break;
6099 
6100  // geometric frequency at which to apply rational reconstruction
6101  case SoPlex::RATREC_FREQ:
6102  break;
6103 
6104  // minimal reduction (sum of removed rows/cols) to continue simplification
6105  case SoPlex::MINRED:
6106  break;
6107 
6109  break;
6110 
6112  break;
6113 
6115  break;
6116 
6117  // accuracy of conjugate gradient method in least squares scaling (higher value leads to more iterations)
6118  case SoPlex::LEASTSQ_ACRCY:
6119  if( _scaler )
6120  _scaler->setRealParam(value);
6121  break;
6122 
6123  // objective offset
6124  case SoPlex::OBJ_OFFSET:
6125  if( _realLP )
6126  _realLP->changeObjOffset(value);
6127  if( _rationalLP )
6128  _rationalLP->changeObjOffset(value);
6129  break;
6130 
6131  default:
6132  return false;
6133  }
6134 
6135  _currentSettings->_realParamValues[param] = tmp_value;
6136  return true;
6137  }
6138 
6139 
6140 
6141 #ifdef SOPLEX_WITH_RATIONALPARAM
6142  /// sets rational parameter value; returns true on success
6143  bool SoPlex::setRationalParam(const RationalParam param, const Rational value, const bool init)
6144  {
6145  assert(param >= 0);
6146  assert(param < RATIONALPARAM_COUNT);
6147  assert(init || _isConsistent());
6148 
6149  if( !init && value == rationalParam(param) )
6150  return true;
6151 
6152  if( value < _currentSettings->rationalParam.lower[param] || value > _currentSettings->rationalParam.upper[param] )
6153  return false;
6154 
6155  switch( param )
6156  {
6157  default:
6158  // currently, there are no rational-valued parameters
6159  return false;
6160  }
6161 
6162  _currentSettings->_rationalParamValues[param] = value;
6163  return true;
6164  }
6165 #endif
6166 
6167 
6168 
6169  /// sets parameter settings; returns true on success
6170  bool SoPlex::setSettings(const Settings& newSettings, const bool init)
6171  {
6172  assert(init || _isConsistent());
6173 
6174  bool success = true;
6175 
6176  *_currentSettings = newSettings;
6177 
6178  for( int i = 0; i < SoPlex::BOOLPARAM_COUNT; i++ )
6179  success &= setBoolParam((BoolParam)i, _currentSettings->_boolParamValues[i], init);
6180 
6181  for( int i = 0; i < SoPlex::INTPARAM_COUNT; i++ )
6182  success &= setIntParam((IntParam)i, _currentSettings->_intParamValues[i], init);
6183 
6184  for( int i = 0; i < SoPlex::REALPARAM_COUNT; i++ )
6185  success &= setRealParam((RealParam)i, _currentSettings->_realParamValues[i], init);
6186 
6187 #ifdef SOPLEX_WITH_RATIONALPARAM
6188  for( int i = 0; i < SoPlex::RATIONALPARAM_COUNT; i++ )
6189  success &= setRationalParam((RationalParam)i, _currentSettings->_rationalParamValues[i], init);
6190 #endif
6191 
6192  assert(_isConsistent());
6193 
6194  return success;
6195  }
6196 
6197  /// resets default parameter settings
6198  void SoPlex::resetSettings(const bool quiet, const bool init)
6199  {
6200  for( int i = 0; i < SoPlex::BOOLPARAM_COUNT; i++ )
6202 
6203  for( int i = 0; i < SoPlex::INTPARAM_COUNT; i++ )
6205 
6206  for( int i = 0; i < SoPlex::REALPARAM_COUNT; i++ )
6208 
6209 #ifdef SOPLEX_WITH_RATIONALPARAM
6210  for( int i = 0; i < SoPlex::RATIONALPARAM_COUNT; i++ )
6211  success &= setRationalParam((RationalParam)i, _currentSettings->rationalParam.defaultValue[i], init);
6212 #endif
6213  }
6214 
6215 
6216  /// print non-default parameter values
6218  {
6219  bool printedValue = false;
6220 
6222 
6223  for( int i = 0; i < SoPlex::BOOLPARAM_COUNT; i++ )
6224  {
6226  continue;
6227 
6228  spxout << "bool:" << _currentSettings->boolParam.name[i] << " = " << (_currentSettings->_boolParamValues[i] ? "true\n" : "false\n");
6229  printedValue = true;
6230  }
6231 
6232  for( int i = 0; i < SoPlex::INTPARAM_COUNT; i++ )
6233  {
6235  continue;
6236 
6237  spxout << "int:" << _currentSettings->intParam.name[i] << " = " << _currentSettings->_intParamValues[i] << "\n";
6238  printedValue = true;
6239  }
6240 
6242 
6243  for( int i = 0; i < SoPlex::REALPARAM_COUNT; i++ )
6244  {
6246  continue;
6247 
6248  spxout << "real:" << _currentSettings->realParam.name[i] << " = " << _currentSettings->_realParamValues[i] << "\n";
6249  printedValue = true;
6250  }
6251 
6252 #ifdef SOPLEX_WITH_RATIONALPARAM
6253  for( int i = 0; i < SoPlex::RATIONALPARAM_COUNT; i++ )
6254  {
6255  if( _currentSettings->_rationalParamValues[i] == _currentSettings->rationalParam.defaultValue[i] )
6256  continue;
6257 
6258  spxout << "rational:" << _currentSettings->rationalParam.name[i] << " = " << _currentSettings->_rationalParamValues[i] << "\n";
6259  printedValue = true;
6260  }
6261 #endif
6262 
6264  {
6265  spxout << "uint:random_seed = " << _solver.random.getSeed() << "\n";
6266  printedValue = true;
6267  }
6268 
6269  if( printedValue )
6270  spxout << std::endl;
6271  }
6272 
6273 
6274 
6275  /// writes settings file; returns true on success
6276  bool SoPlex::saveSettingsFile(const char* filename, const bool onlyChanged) const
6277  {
6278  assert(filename != 0);
6279 
6280  std::ofstream file(filename);
6281  SPxOut::setScientific(file, 16);
6282 
6283  if( !file.good() )
6284  return false;
6285 
6286  file.setf(std::ios::left);
6287 
6288  SPxOut::setFixed(file);
6289 
6290  file << "# SoPlex version " << SOPLEX_VERSION / 100 << "." << (SOPLEX_VERSION / 10) % 10 << "." << SOPLEX_VERSION % 10;
6291 #if SOPLEX_SUBVERSION > 0
6292  file << "." << SOPLEX_SUBVERSION;
6293 #endif
6294  file << "\n";
6295 
6296  for( int i = 0; i < SoPlex::BOOLPARAM_COUNT; i++ )
6297  {
6299  continue;
6300 
6301  file << "\n";
6302  file << "# " << _currentSettings->boolParam.description[i] << "\n";
6303  file << "# range {true, false}, default " << (_currentSettings->boolParam.defaultValue[i] ? "true\n" : "false\n");
6304  file << "bool:" << _currentSettings->boolParam.name[i] << " = " << (_currentSettings->_boolParamValues[i] ? "true\n" : "false\n");
6305  }
6306 
6307  for( int i = 0; i < SoPlex::INTPARAM_COUNT; i++ )
6308  {
6310  continue;
6311 
6312  file << "\n";
6313  file << "# " << _currentSettings->intParam.description[i] << "\n";
6314  file << "# range [" << _currentSettings->intParam.lower[i] << "," << _currentSettings->intParam.upper[i]
6315  << "], default " << _currentSettings->intParam.defaultValue[i] << "\n";
6316  file << "int:" << _currentSettings->intParam.name[i] << " = " << _currentSettings->_intParamValues[i] << "\n";
6317  }
6318 
6319  SPxOut::setScientific(file);
6320 
6321  for( int i = 0; i < SoPlex::REALPARAM_COUNT; i++ )
6322  {
6324  continue;
6325 
6326  file << "\n";
6327  file << "# " << _currentSettings->realParam.description[i] << "\n";
6328  file << "# range [" << _currentSettings->realParam.lower[i] << "," << _currentSettings->realParam.upper[i]
6329  << "], default " << _currentSettings->realParam.defaultValue[i] << "\n";
6330  file << "real:" << _currentSettings->realParam.name[i] << " = " << _currentSettings->_realParamValues[i] << "\n";
6331  }
6332 
6333 #ifdef SOPLEX_WITH_RATIONALPARAM
6334  for( int i = 0; i < SoPlex::RATIONALPARAM_COUNT; i++ )
6335  {
6336  if( onlyChanged && _currentSettings->_rationalParamValues[i] == _currentSettings->rationalParam.defaultValue[i] )
6337  continue;
6338 
6339  file << "\n";
6340  file << "# " << _currentSettings->rationalParam.description[i] << "\n";
6341  file << "# range [" << _currentSettings->rationalParam.lower[i] << "," << _currentSettings->rationalParam.upper[i]
6342  << "], default " << _currentSettings->rationalParam.defaultValue[i] << "\n";
6343  file << "rational:" << _currentSettings->rationalParam.name[i] << " = " << _currentSettings->_rationalParamValues[i] << "\n";
6344  }
6345 #endif
6346 
6347  if( !onlyChanged || _solver.random.getSeed() != DEFAULT_RANDOM_SEED )
6348  {
6349  file << "\n";
6350  file << "# initial random seed used for perturbation\n";
6351  file << "# range [0, " << UINT_MAX << "], default "<< DEFAULT_RANDOM_SEED << "\n";
6352  file << "uint:random_seed = " << _solver.random.getSeed() << "\n";
6353  }
6354 
6355  return true;
6356  }
6357 
6358 
6359 
6360  /// reads settings file; returns true on success
6361  bool SoPlex::loadSettingsFile(const char* filename)
6362  {
6363  assert(filename != 0);
6364 
6365  // start timing
6367 
6368  MSG_INFO1( spxout, spxout << "Loading settings file <" << filename << "> . . .\n" );
6369 
6370  // open file
6371  spxifstream file(filename);
6372 
6373  if( !file )
6374  {
6375  MSG_INFO1( spxout, spxout << "Error opening settings file.\n" );
6376  return false;
6377  }
6378 
6379  // read file
6380  char line[SET_MAX_LINE_LEN];
6381  int lineNumber = 0;
6382  bool readError = false;
6383  bool parseError = false;
6384 
6385  while( !readError && !parseError)
6386  {
6387  lineNumber++;
6388  readError = !file.getline(line, sizeof(line));
6389  if( !readError )
6390  parseError = !_parseSettingsLine(line, lineNumber);
6391  }
6392  readError = readError && !file.eof();
6393 
6394  if( readError && strlen(line) == SET_MAX_LINE_LEN - 1 )
6395  {
6396  MSG_INFO1( spxout, spxout << "Error reading settings file: line " << lineNumber << " in settings file exceeds " << SET_MAX_LINE_LEN - 2 << " characters.\n" );
6397  }
6398  else if( readError )
6399  {
6400  MSG_INFO1( spxout, spxout << "Error reading settings file: line " << lineNumber << ".\n" );
6401  }
6402 
6403  // stop timing
6405 
6406  return !readError;
6407  }
6408 
6409  /// parses one setting string and returns true on success
6410  bool SoPlex::parseSettingsString(char* string)
6411  {
6412  assert(string != 0);
6413  if( string == 0 )
6414  return false;
6415 
6416  char parseString[SET_MAX_LINE_LEN];
6417  strncpy(parseString, string, SET_MAX_LINE_LEN-1);
6418  parseString[SET_MAX_LINE_LEN-1] = '\0';
6419 
6420  char* line = parseString;
6421 
6422  // find the start of the parameter type
6423  while( *line == ' ' || *line == '\t' || *line == '\r' )
6424  line++;
6425  if( *line == '\0' || *line == '\n' || *line == '#' )
6426  return true;
6427  char* paramTypeString = line;
6428 
6429  // find the end of the parameter type
6430  while( *line != ' ' && *line != '\t' && *line != '\r' && *line != '\n' && *line != '#' && *line != '\0' && *line != ':' )
6431  line++;
6432  if( *line == ':' )
6433  {
6434  *line = '\0';
6435  line++;
6436  }
6437  else
6438  {
6439  *line = '\0';
6440  line++;
6441 
6442  // search for the ':' char in the line
6443  while( *line == ' ' || *line == '\t' || *line == '\r' )
6444  line++;
6445  if( *line != ':' )
6446  {
6447  MSG_INFO1( spxout, spxout << "Error parsing setting string: no ':' separating parameter type and name.\n" );
6448  return false;
6449  }
6450  line++;
6451  }
6452 
6453  // find the start of the parameter name
6454  while( *line == ' ' || *line == '\t' || *line == '\r' )
6455  line++;
6456  if( *line == '\0' || *line == '\n' || *line == '#' )
6457  {
6458  MSG_INFO1( spxout, spxout << "Error parsing setting string: no parameter name.\n");
6459  return false;
6460  }
6461  char* paramName = line;
6462 
6463  // find the end of the parameter name
6464  while( *line != ' ' && *line != '\t' && *line != '\r' && *line != '\n' && *line != '#' && *line != '\0' && *line != '=' )
6465  line++;
6466  if( *line == '=' )
6467  {
6468  *line = '\0';
6469  line++;
6470  }
6471  else
6472  {
6473  *line = '\0';
6474  line++;
6475 
6476  // search for the '=' char in the line
6477  while( *line == ' ' || *line == '\t' || *line == '\r' )
6478  line++;
6479  if( *line != '=' )
6480  {
6481  MSG_INFO1( spxout, spxout << "Error parsing setting string: no '=' after parameter name.\n" );
6482  return false;
6483  }
6484  line++;
6485  }
6486 
6487  // find the start of the parameter value string
6488  while( *line == ' ' || *line == '\t' || *line == '\r' )
6489  line++;
6490  if( *line == '\0' || *line == '\n' || *line == '#' )
6491  {
6492  MSG_INFO1( spxout, spxout << "Error parsing setting string: no parameter value.\n");
6493  return false;
6494  }
6495  char* paramValueString = line;
6496 
6497  // find the end of the parameter value string
6498  while( *line != ' ' && *line != '\t' && *line != '\r' && *line != '\n' && *line != '#' && *line != '\0' )
6499  line++;
6500  if( *line != '\0' )
6501  {
6502  // check, if the rest of the line is clean
6503  *line = '\0';
6504  line++;
6505  while( *line == ' ' || *line == '\t' || *line == '\r' )
6506  line++;
6507  if( *line != '\0' && *line != '\n' && *line != '#' )
6508  {
6509  MSG_INFO1( spxout, spxout << "Error parsing setting string: additional character '" << *line << "' after parameter value.\n" );
6510  return false;
6511  }
6512  }
6513 
6514  // check whether we have a bool parameter
6515  if( strncmp(paramTypeString, "bool", 4) == 0 )
6516  {
6517  for( int param = 0; ; param++ )
6518  {
6519  if( param >= SoPlex::BOOLPARAM_COUNT )
6520  {
6521  MSG_INFO1( spxout, spxout << "Error parsing setting string: unknown parameter name <" << paramName << ">.\n" );
6522  return false;
6523  }
6524  else if( strncmp(paramName, _currentSettings->boolParam.name[param].c_str(), SET_MAX_LINE_LEN) == 0 )
6525  {
6526  if( strncasecmp(paramValueString, "true", 4) == 0
6527  || strncasecmp(paramValueString, "TRUE", 4) == 0
6528  || strncasecmp(paramValueString, "t", 4) == 0
6529  || strncasecmp(paramValueString, "T", 4) == 0
6530  || strtol(paramValueString, NULL, 4) == 1 )
6531  {
6532  setBoolParam((SoPlex::BoolParam)param, true);
6533  break;
6534  }
6535  else if( strncasecmp(paramValueString, "false", 5) == 0
6536  || strncasecmp(paramValueString, "FALSE", 5) == 0
6537  || strncasecmp(paramValueString, "f", 5) == 0
6538  || strncasecmp(paramValueString, "F", 5) == 0
6539  || strtol(paramValueString, NULL, 5) == 0 )
6540  {
6541  setBoolParam((SoPlex::BoolParam)param, false);
6542  break;
6543  }
6544  else
6545  {
6546  MSG_INFO1( spxout, spxout << "Error parsing setting string: invalid value <" << paramValueString << "> for bool parameter <" << paramName << ">.\n" );
6547  return false;
6548  }
6549  }
6550  }
6551 
6552  return true;
6553  }
6554 
6555  // check whether we have an integer parameter
6556  if( strncmp(paramTypeString, "int", 3) == 0 )
6557  {
6558  for( int param = 0; ; param++ )
6559  {
6560  if( param >= SoPlex::INTPARAM_COUNT )
6561  {
6562  MSG_INFO1( spxout, spxout << "Error parsing setting string: unknown parameter name <" << paramName << ">.\n" );
6563  return false;
6564  }
6565  else if( strncmp(paramName, _currentSettings->intParam.name[param].c_str(), SET_MAX_LINE_LEN) == 0 )
6566  {
6567  int value;
6568 
6569  if( sscanf(paramValueString, "%d", &value) == 1 && setIntParam((SoPlex::IntParam)param, value, false) )
6570  break;
6571  else
6572  {
6573  MSG_INFO1( spxout, spxout << "Error parsing setting string: invalid value <" << paramValueString << "> for int parameter <" << paramName << ">.\n" );
6574  return false;
6575  }
6576  }
6577  }
6578 
6579  return true;
6580  }
6581 
6582  // check whether we have a real parameter
6583  if( strncmp(paramTypeString, "real", 4) == 0 )
6584  {
6585  for( int param = 0; ; param++ )
6586  {
6587  if( param >= SoPlex::REALPARAM_COUNT )
6588  {
6589  MSG_INFO1( spxout, spxout << "Error parsing setting string: unknown parameter name <" << paramName << ">.\n" );
6590  return false;
6591  }
6592  else if( strncmp(paramName, _currentSettings->realParam.name[param].c_str(), SET_MAX_LINE_LEN) == 0 )
6593  {
6594  Real value;
6595 
6596  if( sscanf(paramValueString, "%" REAL_FORMAT, &value) == 1 && setRealParam((SoPlex::RealParam)param, value) )
6597  break;
6598  else
6599  {
6600  MSG_INFO1( spxout, spxout << "Error parsing setting string: invalid value <" << paramValueString << "> for real parameter <" << paramName << ">.\n" );
6601  return false;
6602  }
6603  }
6604  }
6605 
6606  return true;
6607  }
6608 
6609 #ifdef SOPLEX_WITH_RATIONALPARAM
6610  // check whether we have a rational parameter
6611  if( strncmp(paramTypeString, "rational", 8) == 0 )
6612  {
6613  for( int param = 0; ; param++ )
6614  {
6615  if( param >= SoPlex::RATIONALPARAM_COUNT )
6616  {
6617  MSG_INFO1( spxout, spxout << "Error parsing setting string: unknown parameter name <" << paramName << ">.\n" );
6618  return false;
6619  }
6620  else if( strncmp(paramName, _currentSettings->rationalParam.name[param].c_str(), SET_MAX_LINE_LEN) == 0 )
6621  {
6622  Rational value;
6623 
6624  if( readStringRational(paramValueString, value) && setRationalParam((SoPlex::RationalParam)param, value) )
6625  break;
6626  else
6627  {
6628  MSG_INFO1( spxout, spxout << "Error parsing setting string: invalid value <" << paramValueString << "> for rational parameter <" << paramName << ">.\n" );
6629  return false;
6630  }
6631  }
6632  }
6633 
6634  return true;
6635  }
6636 #endif
6637 
6638  // check whether we have the random seed
6639  if( strncmp(paramTypeString, "uint", 4) == 0 )
6640  {
6641  if( strncmp(paramName, "random_seed", 11) == 0 )
6642  {
6643  unsigned int value;
6644  char format[SPX_MAXSTRLEN];
6645  spxSnprintf(format, sizeof(format), "%%%du", (int) sizeof(value)-1);
6646 
6647  if( sscanf(paramValueString, format, &value) == 1 )
6648  {
6649 
6650  setRandomSeed(value);
6651  return true;
6652  }
6653  }
6654 
6655  MSG_INFO1( spxout, spxout << "Error parsing setting string for uint parameter <random_seed>.\n" );
6656  return false;
6657  }
6658 
6659  MSG_INFO1( spxout, spxout << "Error parsing setting string: invalid parameter type <" << paramTypeString << "> for parameter <" << paramName << ">.\n" );
6660 
6661  return false;
6662  }
6663 
6664 
6665 
6666 
6667  /// prints solution statistics
6668  void SoPlex::printSolutionStatistics(std::ostream& os)
6669  {
6672  {
6673  os << "Solution (real) : \n"
6674  << " Objective value : " << objValueReal() << "\n";
6675  }
6676  else if( _lastSolveMode == SOLVEMODE_RATIONAL )
6677  {
6678  os << "Solution (rational) : \n"
6679  << " Objective value : " << rationalToString(objValueRational()) << "\n";
6680  os << "Size (base 2/10) : \n"
6681  << " Total primal : " << totalSizePrimalRational() << " / " << totalSizePrimalRational(10) << "\n"
6682  << " Total dual : " << totalSizeDualRational() << " / " << totalSizeDualRational(10) << "\n"
6683  << " DLCM primal : " << dlcmSizePrimalRational() << " / " << dlcmSizePrimalRational(10) << "\n"
6684  << " DLCM dual : " << dlcmSizeDualRational() << " / " << dlcmSizeDualRational(10) << "\n"
6685  << " DMAX primal : " << dmaxSizePrimalRational() << " / " << dmaxSizePrimalRational(10) << "\n"
6686  << " DMAX dual : " << dmaxSizeDualRational() << " / " << dmaxSizeDualRational(10) << "\n";
6687  }
6688  else
6689  {
6690  os << "Solution : \n"
6691  << " Objective value : -\n";
6692  }
6693 
6696  {
6697  Rational maxviol;
6698  Rational sumviol;
6699 
6700  os << "Violation (rational): \n";
6701  if( getBoundViolationRational(maxviol, sumviol) )
6702  os << " Max/sum bound : " << rationalToString(maxviol) << " / " << rationalToString(sumviol) << "\n";
6703  else
6704  os << " Max/sum bound : - / -\n";
6705  if( getRowViolationRational(maxviol, sumviol) )
6706  os << " Max/sum row : " << rationalToString(maxviol) << " / " << rationalToString(sumviol) << "\n";
6707  else
6708  os << " Max/sum row : - / -\n";
6709  if( getRedCostViolationRational(maxviol, sumviol) )
6710  os << " Max/sum redcost : " << rationalToString(maxviol) << " / " << rationalToString(sumviol) << "\n";
6711  else
6712  os << " Max/sum redcost : - / -\n";
6713  if( getDualViolationRational(maxviol, sumviol) )
6714  os << " Max/sum dual : " << rationalToString(maxviol) << " / " << rationalToString(sumviol) << "\n";
6715  else
6716  os << " Max/sum dual : - / -\n";
6717  }
6718  else
6719  {
6720  Real maxviol;
6721  Real sumviol;
6722 
6723  os << "Violations (real) : \n";
6724  if( getBoundViolationReal(maxviol, sumviol) )
6725  os << " Max/sum bound : " << maxviol << " / " << sumviol << "\n";
6726  else
6727  os << " Max/sum bound : - / -\n";
6728  if( getRowViolationReal(maxviol, sumviol) )
6729  os << " Max/sum row : " << maxviol << " / " << sumviol << "\n";
6730  else
6731  os << " Max/sum row : - / -\n";
6732  if( getRedCostViolationReal(maxviol, sumviol) )
6733  os << " Max/sum redcost : " << maxviol << " / " << sumviol << "\n";
6734  else
6735  os << " Max/sum redcost : - / -\n";
6736  if( getDualViolationReal(maxviol, sumviol) )
6737  os << " Max/sum dual : " << maxviol << " / " << sumviol << "\n";
6738  else
6739  os << " Max/sum dual : - / -\n";
6740  }
6741  }
6742 
6743 
6744  /// prints statistics on solving process
6745  void SoPlex::printSolvingStatistics(std::ostream& os)
6746  {
6747  assert(_statistics != 0);
6748  _statistics->print(os);
6749  }
6750 
6751 
6752 
6753  /// prints short statistics
6754  void SoPlex::printShortStatistics(std::ostream& os)
6755  {
6756  printStatus(os, _status);
6757  SPxOut::setFixed(os, 2);
6758  os << "Solving time (sec) : " << _statistics->solvingTime->time() << "\n"
6759  << "Iterations : " << _statistics->iterations << "\n";
6761  os << "Objective value : " << objValueReal() << "\n";
6762  }
6763 
6764 
6765 
6766  /// prints complete statistics
6767  void SoPlex::printStatistics(std::ostream& os)
6768  {
6769  SPxOut::setFixed(os, 2);
6770 
6771  printStatus(os, _status);
6772 
6773  os << "Original problem : \n";
6776  else
6777  {
6780  else
6782  }
6783 
6784  os << "Objective sense : " << (intParam(SoPlex::OBJSENSE) == SoPlex::OBJSENSE_MINIMIZE ? "minimize\n" : "maximize\n");
6787  }
6788 
6789  /// prints status
6790  void SoPlex::printStatus(std::ostream& os, SPxSolver::Status stat)
6791  {
6792  os << "SoPlex status : ";
6793 
6794  switch( stat )
6795  {
6796  case SPxSolver::ERROR:
6797  os << "error [unspecified]";
6798  break;
6800  os << "error [no ratiotester loaded]";
6801  break;
6802  case SPxSolver::NO_PRICER:
6803  os << "error [no pricer loaded]";
6804  break;
6805  case SPxSolver::NO_SOLVER:
6806  os << "error [no linear solver loaded]";
6807  break;
6808  case SPxSolver::NOT_INIT:
6809  os << "error [not initialized]";
6810  break;
6812  os << "solving aborted [cycling]";
6813  break;
6814  case SPxSolver::ABORT_TIME:
6815  os << "solving aborted [time limit reached]";
6816  break;
6817  case SPxSolver::ABORT_ITER:
6818  os << "solving aborted [iteration limit reached]";
6819  break;
6821  os << "solving aborted [objective limit reached]";
6822  break;
6823  case SPxSolver::NO_PROBLEM:
6824  os << "no problem loaded";
6825  break;
6826  case SPxSolver::REGULAR:
6827  os << "basis is regular";
6828  break;
6829  case SPxSolver::SINGULAR:
6830  os << "basis is singular";
6831  break;
6832  case SPxSolver::OPTIMAL:
6833  os << "problem is solved [optimal]";
6834  break;
6835  case SPxSolver::UNBOUNDED:
6836  os << "problem is solved [unbounded]";
6837  break;
6838  case SPxSolver::INFEASIBLE:
6839  os << "problem is solved [infeasible]";
6840  break;
6841  case SPxSolver::INForUNBD:
6842  os << "problem is solved [infeasible or unbounded]";
6843  break;
6844  default:
6845  case SPxSolver::UNKNOWN:
6846  os << "unknown";
6847  break;
6848  }
6849 
6850  os << "\n";
6851  }
6852 
6853 
6854 
6855  /// prints version and compilation options
6857  {
6858  // do not use preprocessor directives within the MSG_INFO1 macro
6859 #if (SOPLEX_SUBVERSION > 0)
6860  MSG_INFO1( spxout, spxout << "SoPlex version " << SOPLEX_VERSION/100
6861  << "." << (SOPLEX_VERSION % 100)/10
6862  << "." << SOPLEX_VERSION % 10
6863  << "." << SOPLEX_SUBVERSION );
6864 #else
6865  MSG_INFO1( spxout, spxout << "SoPlex version " << SOPLEX_VERSION/100
6866  << "." << (SOPLEX_VERSION % 100)/10
6867  << "." << SOPLEX_VERSION % 10 );
6868 #endif
6869 
6870 #ifndef NDEBUG
6871  MSG_INFO1( spxout, spxout << " [mode: debug]" );
6872 #else
6873  MSG_INFO1( spxout, spxout << " [mode: optimized]" );
6874 #endif
6875 
6876  MSG_INFO1( spxout, spxout << " [precision: " << (int)sizeof(Real) << " byte]" );
6877 
6878 #ifdef SOPLEX_WITH_GMP
6879 #ifdef mpir_version
6880  MSG_INFO1( spxout, spxout << " [rational: MPIR " << mpir_version << "]" );
6881 #else
6882  MSG_INFO1( spxout, spxout << " [rational: GMP " << gmp_version << "]" );
6883 #endif
6884 #else
6885  MSG_INFO1( spxout, spxout << " [rational: long double]" );
6886 #endif
6887 
6888  MSG_INFO1( spxout, spxout << " [githash: " << getGitHash() << "]\n" );
6889  }
6890 
6891 
6892 
6893  /// checks if real LP and rational LP are in sync; dimensions will always be compared,
6894  /// vector and matrix values only if the respective parameter is set to true.
6895  /// If quiet is set to true the function will only display which vectors are different.
6896  bool SoPlex::areLPsInSync(const bool checkVecVals, const bool checkMatVals, const bool quiet) const
6897  {
6898  bool result = true;
6899  bool nRowsMatch = true;
6900  bool nColsMatch = true;
6901  bool rhsDimMatch = true;
6902  bool lhsDimMatch = true;
6903  bool maxObjDimMatch = true;
6904  bool upperDimMatch = true;
6905  bool lowerDimMatch = true;
6906 
6907  // compare number of Rows
6908  if( _realLP->nRows() != _rationalLP->nRows() )
6909  {
6910  MSG_INFO1( spxout, spxout << "The number of Rows in the Real LP does not match the one in the Rational LP."
6911  << " Real LP: " << _realLP->nRows() << " Rational LP: " << _rationalLP->nRows() << std::endl);
6912  result = false;
6913  nRowsMatch = false;
6914  }
6915 
6916  // compare number of Columns
6917  if( _realLP->nCols() != _rationalLP->nCols() )
6918  {
6919  MSG_INFO1( spxout, spxout << "The number of Columns in the Real LP does not match the one in the Rational LP."
6920  << " Real LP: " << _realLP->nCols() << " Rational LP: " << _rationalLP->nCols() << std::endl);
6921  result = false;
6922  nColsMatch = false;
6923  }
6924 
6925  // compare number of nonZeros
6926  if( _realLP->nNzos() != _rationalLP->nNzos() )
6927  {
6928  MSG_INFO1( spxout, spxout << "The number of nonZeros in the Real LP does not match the one in the Rational LP."
6929  << " Real LP: " << _realLP->nNzos() << " Rational LP: " << _rationalLP->nNzos() << std::endl);
6930  result = false;
6931  }
6932 
6933  // compare the dimensions of the right hand side vectors
6934  if( _realLP->rhs().dim() != _rationalLP->rhs().dim() )
6935  {
6936  MSG_INFO1( spxout, spxout << "The dimension of the right hand side vector of the Real LP does not match the one of the Rational LP."
6937  << " Real LP: " << _realLP->rhs().dim() << " Rational LP: " << _rationalLP->rhs().dim() << std::endl);
6938  result = false;
6939  rhsDimMatch = false;
6940 
6941  }
6942 
6943  // compare the dimensions of the left hand side vectors
6944  if( _realLP->lhs().dim() != _rationalLP->lhs().dim() )
6945  {
6946  MSG_INFO1( spxout, spxout << "The dimension of the left hand side vector of the Real LP does not match the one of the Rational LP."
6947  << " Real LP: " << _realLP->lhs().dim() << " Rational LP: " << _rationalLP->lhs().dim() << std::endl);
6948  result = false;
6949  lhsDimMatch = false;
6950  }
6951 
6952  // compare the dimensions of the objective function vectors
6953  if( _realLP->maxObj().dim() != _rationalLP->maxObj().dim() )
6954  {
6955  MSG_INFO1( spxout, spxout << "The dimension of the objective function vector of the Real LP does not match the one of the Rational LP."
6956  << " Real LP: " << _realLP->maxObj().dim() << " Rational LP: " << _rationalLP->maxObj().dim() << std::endl);
6957  result = false;
6958  maxObjDimMatch = false;
6959  }
6960 
6961  // compare the sense
6962  if( (int)_realLP->spxSense() != (int)_rationalLP->spxSense() )
6963  {
6964  MSG_INFO1( spxout, spxout << "The objective function sense of the Real LP does not match the one of the Rational LP."
6965  << " Real LP: " << (_realLP->spxSense() == SPxLPReal::MINIMIZE ? "MIN" : "MAX")
6966  << " Rational LP: " << (_rationalLP->spxSense() == SPxLPRational::MINIMIZE ? "MIN" : "MAX") << std::endl);
6967  result = false;
6968  }
6969 
6970  // compare the dimensions of upper bound vectors
6971  if( _realLP->upper().dim() != _rationalLP->upper().dim() )
6972  {
6973  MSG_INFO1( spxout, spxout << "The dimension of the upper bound vector of the Real LP does not match the one of the Rational LP."
6974  << " Real LP: " << _realLP->upper().dim() << " Rational LP: " << _rationalLP->upper().dim() << std::endl);
6975  result = false;
6976  upperDimMatch = false;
6977  }
6978 
6979  // compare the dimensions of the objective function vectors
6980  if( _realLP->lower().dim() != _rationalLP->lower().dim() )
6981  {
6982  MSG_INFO1( spxout, spxout << "The dimension of the lower bound vector of the Real LP does not match the one of the Rational LP."
6983  << " Real LP: " << _realLP->lower().dim() << " Rational LP: " << _rationalLP->lower().dim() << std::endl);
6984  result = false;
6985  lowerDimMatch = false;
6986  }
6987 
6988  // compares the values of the rhs, lhs, maxObj, upper, lower vectors
6989  if( checkVecVals )
6990  {
6991  bool rhsValMatch = true;
6992  bool lhsValMatch = true;
6993  bool maxObjValMatch = true;
6994  bool upperValMatch = true;
6995  bool lowerValMatch = true;
6996 
6997  // compares the values of the right hand side vectors
6998  if( rhsDimMatch )
6999  {
7000  for( int i = 0; i < _realLP->rhs().dim(); i++ )
7001  {
7002  if( (GE(_realLP->rhs()[i], realParam(SoPlex::INFTY)) != (_rationalLP->rhs()[i] >= _rationalPosInfty))
7004  && !_rationalLP->rhs()[i].isAdjacentTo((double)_realLP->rhs()[i])) )
7005  {
7006  if( !quiet )
7007  {
7008  MSG_INFO1( spxout, spxout << "Entries number " << i << " of the right hand side vectors don't match."
7009  << " Real LP: " << _realLP->rhs()[i] << " Rational LP: " << _rationalLP->rhs()[i] << std::endl);
7010  }
7011  rhsValMatch = false;
7012  result = false;
7013  }
7014  }
7015 
7016  if( !rhsValMatch && quiet )
7017  {
7018  MSG_INFO1( spxout, spxout << "The values of the right hand side vectors don't match." << std::endl );
7019  }
7020  }
7021 
7022  // compares the values of the left hand side vectors
7023  if( lhsDimMatch )
7024  {
7025  for( int i = 0; i < _realLP->lhs().dim(); i++ )
7026  {
7027  if( (LE(_realLP->lhs()[i], -realParam(SoPlex::INFTY)) != (_rationalLP->lhs()[i] <= _rationalNegInfty))
7029  && !_rationalLP->lhs()[i].isAdjacentTo((double)_realLP->lhs()[i])) )
7030  {
7031  if( !quiet )
7032  {
7033  MSG_INFO1( spxout, spxout << "Entries number " << i << " of the left hand side vectors don't match."
7034  << " Real LP: " << _realLP->lhs()[i] << " Rational LP: " << _rationalLP->lhs()[i] << std::endl);
7035  }
7036  lhsValMatch = false;
7037  result = false;
7038  }
7039  }
7040 
7041  if( !lhsValMatch && quiet )
7042  {
7043  MSG_INFO1( spxout, spxout << "The values of the left hand side vectors don't match." << std::endl );
7044  }
7045  }
7046 
7047  // compares the values of the objective function vectors
7048  if( maxObjDimMatch )
7049  {
7050  for( int i = 0; i < _realLP->maxObj().dim(); i++ )
7051  {
7052  if( !_rationalLP->maxObj()[i].isAdjacentTo((double)_realLP->maxObj()[i]) )
7053  {
7054  if( !quiet )
7055  {
7056  MSG_INFO1( spxout, spxout << "Entries number " << i << " of the objective function vectors don't match."
7057  << " Real LP: " << _realLP->maxObj()[i] << " Rational LP: " << _rationalLP->maxObj()[i] << std::endl);
7058  }
7059  maxObjValMatch = false;
7060  result = false;
7061  }
7062  }
7063 
7064  if( !maxObjValMatch && quiet )
7065  {
7066  MSG_INFO1( spxout, spxout << "The values of the objective function vectors don't match." << std::endl );
7067  }
7068  }
7069 
7070  // compares the values of the upper bound vectors
7071  if( upperDimMatch )
7072  {
7073  for( int i = 0; i < _realLP->upper().dim(); i++ )
7074  {
7077  && !_rationalLP->upper()[i].isAdjacentTo((double)_realLP->upper()[i])) )
7078  {
7079  if( !quiet )
7080  {
7081  MSG_INFO1( spxout, spxout << "Entries number " << i << " of the upper bound vectors don't match."
7082  << " Real LP: " << _realLP->upper()[i] << " Rational LP: " << _rationalLP->upper()[i] << std::endl);
7083  }
7084  upperValMatch = false;
7085  result = false;
7086  }
7087  }
7088 
7089  if( !upperValMatch && quiet )
7090  {
7091  MSG_INFO1( spxout, spxout << "The values of the upper bound vectors don't match." << std::endl );
7092  }
7093  }
7094 
7095  // compares the values of the lower bound vectors
7096  if( lowerDimMatch )
7097  {
7098  for( int i = 0; i < _realLP->lower().dim(); i++ )
7099  {
7102  && !_rationalLP->lower()[i].isAdjacentTo((double)_realLP->lower()[i])) )
7103  {
7104  if( !quiet )
7105  {
7106  MSG_INFO1( spxout, spxout << "Entries number " << i << " of the lower bound vectors don't match."
7107  << " Real LP: " << _realLP->lower()[i] << " Rational LP: " << _rationalLP->lower()[i] << std::endl);
7108  }
7109  lowerValMatch = false;
7110  result = false;
7111  }
7112  }
7113 
7114  if( !lowerValMatch && quiet )
7115  {
7116  MSG_INFO1( spxout, spxout << "The values of the lower bound vectors don't match." << std::endl );
7117  }
7118  }
7119  }
7120 
7121  // compare the values of the matrix
7122  if( checkMatVals && nRowsMatch && nColsMatch )
7123  {
7124  bool matrixValMatch = true;
7125 
7126  for( int i = 0; i < _realLP->nCols() ; i++ )
7127  {
7128  for( int j = 0;j < _realLP->nRows() ; j++ )
7129  {
7130  if( !_rationalLP->colVector(i)[j].isAdjacentTo((double)_realLP->colVector(i)[j]) )
7131  {
7132  if( !quiet )
7133  {
7134  MSG_INFO1( spxout, spxout << "Entries number " << j << " of column number " << i << " don't match."
7135  << " Real LP: " << _realLP->colVector(i)[j] << " Rational LP: " << _rationalLP->colVector(i)[j] << std::endl);
7136  }
7137  matrixValMatch = false;
7138  result = false;
7139  }
7140  }
7141  }
7142 
7143  if( !matrixValMatch && quiet )
7144  {
7145  MSG_INFO1( spxout, spxout << "The values of the matrices don't match." << std::endl );
7146  }
7147  }
7148 
7149  return result;
7150  }
7151 
7152 
7153 
7154  /// set the random seed of the solver instance
7155  void SoPlex::setRandomSeed(unsigned int seed)
7156  {
7157  _solver.random.setSeed(seed);
7158  }
7159 
7160 
7161 
7162  /// returns the current random seed of the solver instance or the one stored in the settings
7163  unsigned int SoPlex::randomSeed() const
7164  {
7165  return _solver.random.getSeed();
7166  }
7167 
7168 
7169 
7170  /// extends sparse vector to hold newmax entries if and only if it holds no more free entries
7171  void SoPlex::_ensureDSVectorRationalMemory(DSVectorRational& vec, const int newmax) const
7172  {
7173  assert(newmax > vec.size());
7174  if( vec.size() >= vec.max() )
7175  vec.setMax(newmax);
7176  }
7177 
7178 
7179 
7180  /// creates a permutation for removing rows/columns from an array of indices
7181  void SoPlex::_idxToPerm(int* idx, int idxSize, int* perm, int permSize) const
7182  {
7183  assert(idx != 0);
7184  assert(idxSize >= 0);
7185  assert(perm != 0);
7186  assert(permSize >= 0);
7187 
7188  for( int i = 0; i < permSize; i++ )
7189  perm[i] = i;
7190 
7191  for( int i = 0; i < idxSize; i++ )
7192  {
7193  assert(idx[i] >= 0);
7194  assert(idx[i] < permSize);
7195  perm[idx[i]] = -1;
7196  }
7197  }
7198 
7199 
7200 
7201  /// creates a permutation for removing rows/columns from a range of indices
7202  void SoPlex::_rangeToPerm(int start, int end, int* perm, int permSize) const
7203  {
7204  assert(perm != 0);
7205  assert(permSize >= 0);
7206 
7207  for( int i = 0; i < permSize; i++ )
7208  perm[i] = (i < start || i > end) ? i : -1;
7209  }
7210 
7211 
7212 
7213  /// checks consistency
7215  {
7216  assert(_statistics != 0);
7217  assert(_currentSettings != 0);
7218 
7219  assert(_realLP != 0);
7221 
7222  assert(_realLP != &_solver || _isRealLPLoaded);
7223  assert(_realLP == &_solver || !_isRealLPLoaded);
7224 
7230 
7231  assert(_rationalLP == 0 || _colTypes.size() == numColsRational());
7232  assert(_rationalLP == 0 || _rowTypes.size() == numRowsRational());
7233 
7234  return true;
7235  }
7236 
7237 
7238 
7239  /// should solving process be stopped?
7240  bool SoPlex::_isSolveStopped(bool& stoppedTime, bool& stoppedIter) const
7241  {
7242  assert(_statistics != 0);
7243 
7245  stoppedIter = (intParam(ITERLIMIT) >= 0 && _statistics->iterations >= intParam(ITERLIMIT))
7248 
7249  return stoppedTime || stoppedIter;
7250  }
7251 
7252 
7253 
7254  /// determines RangeType from real bounds
7255  SoPlex::RangeType SoPlex::_rangeTypeReal(const Real& lower, const Real& upper) const
7256  {
7257  assert(lower <= upper);
7258 
7259  if( lower <= -infinity )
7260  {
7261  if( upper >= infinity )
7262  return RANGETYPE_FREE;
7263  else
7264  return RANGETYPE_UPPER;
7265  }
7266  else
7267  {
7268  if( upper >= infinity )
7269  return RANGETYPE_LOWER;
7270  else if( lower == upper )
7271  return RANGETYPE_FIXED;
7272  else
7273  return RANGETYPE_BOXED;
7274  }
7275  }
7276 
7277 
7278 
7279  /// determines RangeType from rational bounds
7281  {
7282  assert(lower <= upper);
7283 
7284  if( lower <= _rationalNegInfty )
7285  {
7286  if( upper >= _rationalPosInfty )
7287  return RANGETYPE_FREE;
7288  else
7289  return RANGETYPE_UPPER;
7290  }
7291  else
7292  {
7293  if( upper >= _rationalPosInfty )
7294  return RANGETYPE_LOWER;
7295  else if( lower == upper )
7296  return RANGETYPE_FIXED;
7297  else
7298  return RANGETYPE_BOXED;
7299  }
7300  }
7301 
7302 
7303 
7304  /// switches RANGETYPE_LOWER to RANGETYPE_UPPER and vice versa
7306  {
7307  if( rangeType == RANGETYPE_LOWER )
7308  return RANGETYPE_UPPER;
7309  else if( rangeType == RANGETYPE_UPPER )
7310  return RANGETYPE_LOWER;
7311  else
7312  return rangeType;
7313  }
7314 
7315 
7316 
7317  /// checks whether RangeType corresponds to finite lower bound
7318  bool SoPlex::_lowerFinite(const RangeType& rangeType) const
7319  {
7320  return (rangeType == RANGETYPE_LOWER || rangeType == RANGETYPE_BOXED || rangeType == RANGETYPE_FIXED);
7321  }
7322 
7323 
7324 
7325  /// checks whether RangeType corresponds to finite upper bound
7326  bool SoPlex::_upperFinite(const RangeType& rangeType) const
7327  {
7328  return (rangeType == RANGETYPE_UPPER || rangeType == RANGETYPE_BOXED || rangeType == RANGETYPE_FIXED);
7329  }
7330 
7331 
7332 
7333  /// adds a single row to the real LP and adjusts basis
7334  void SoPlex::_addRowReal(const LPRowReal& lprow)
7335  {
7336  assert(_realLP != 0);
7337 
7338  bool scale = _realLP->isScaled();
7339  _realLP->addRow(lprow, scale);
7340 
7341  if( _isRealLPLoaded )
7343  else if( _hasBasis )
7345 
7347  }
7348 
7349 
7350 
7351  /// adds a single row to the real LP and adjusts basis
7352  void SoPlex::_addRowReal(Real lhs, const SVectorReal& lprow, Real rhs)
7353  {
7354  assert(_realLP != 0);
7355 
7356  bool scale = _realLP->isScaled();
7357  _realLP->addRow(lhs, lprow, rhs, scale);
7358 
7359  if( _isRealLPLoaded )
7361  else if( _hasBasis )
7363 
7365  }
7366 
7367 
7368 
7369  /// adds multiple rows to the real LP and adjusts basis
7370  void SoPlex::_addRowsReal(const LPRowSetReal& lprowset)
7371  {
7372  assert(_realLP != 0);
7373 
7374  bool scale = _realLP->isScaled();
7375  _realLP->addRows(lprowset, scale);
7376 
7377  if( _isRealLPLoaded )
7379  else if( _hasBasis )
7381 
7383  }
7384 
7385 
7386  /// adds a single column to the real LP and adjusts basis
7387  void SoPlex::_addColReal(const LPColReal& lpcol)
7388  {
7389  assert(_realLP != 0);
7390 
7391  bool scale = _realLP->isScaled();
7392  _realLP->addCol(lpcol, scale);
7393 
7394  if( _isRealLPLoaded )
7396  else if( _hasBasis )
7397  {
7398  if( lpcol.lower() > -realParam(SoPlex::INFTY) )
7400  else if( lpcol.upper() < realParam(SoPlex::INFTY) )
7402  else
7404  }
7405 
7407  }
7408 
7409 
7410 
7411  /// adds a single column to the real LP and adjusts basis
7412  void SoPlex::_addColReal(Real obj, Real lower, const SVectorReal& lpcol, Real upper)
7413  {
7414  assert(_realLP != 0);
7415 
7416  bool scale = _realLP->isScaled();
7417  _realLP->addCol(obj, lower, lpcol, upper, scale);
7418 
7419  if( _isRealLPLoaded )
7421  else if( _hasBasis )
7423 
7425  }
7426 
7427 
7428 
7429  /// adds multiple columns to the real LP and adjusts basis
7430  void SoPlex::_addColsReal(const LPColSetReal& lpcolset)
7431  {
7432  assert(_realLP != 0);
7433 
7434  bool scale = _realLP->isScaled();
7435  _realLP->addCols(lpcolset, scale);
7436 
7437  if( _isRealLPLoaded )
7439  else if( _hasBasis )
7440  {
7441  for( int i = 0; i < lpcolset.num(); i++ )
7442  {
7443  if( lpcolset.lower(i) > -realParam(SoPlex::INFTY) )
7445  else if( lpcolset.upper(i) < realParam(SoPlex::INFTY) )
7447  else
7449  }
7450  }
7451 
7453  }
7454 
7455 
7456  /// replaces row \p i with \p lprow and adjusts basis
7457  void SoPlex::_changeRowReal(int i, const LPRowReal& lprow)
7458  {
7459  assert(_realLP != 0);
7460 
7461  bool scale = _realLP->isScaled();
7462  _realLP->changeRow(i, lprow, scale);
7463 
7464  if( _isRealLPLoaded )
7466  else if( _hasBasis )
7467  {
7469  _hasBasis = false;
7470  else if( _basisStatusRows[i] == SPxSolver::ON_LOWER && lprow.lhs() <= -realParam(SoPlex::INFTY) )
7472  else if( _basisStatusRows[i] == SPxSolver::ON_UPPER && lprow.rhs() >= realParam(SoPlex::INFTY) )
7474  }
7475 
7477  }
7478 
7479 
7480 
7481  /// changes left-hand side vector for constraints to \p lhs and adjusts basis
7483  {
7484  assert(_realLP != 0);
7485 
7486  bool scale = _realLP->isScaled();
7487  _realLP->changeLhs(lhs, scale);
7488 
7489  if( _isRealLPLoaded )
7491  else if( _hasBasis )
7492  {
7493  for( int i = numRowsReal() - 1; i >= 0; i-- )
7494  {
7495  if( _basisStatusRows[i] == SPxSolver::ON_LOWER && lhs[i] <= -realParam(SoPlex::INFTY) )
7497  }
7498  }
7499  }
7500 
7501 
7502 
7503  /// changes left-hand side of row \p i to \p lhs and adjusts basis
7504  void SoPlex::_changeLhsReal(int i, const Real& lhs)
7505  {
7506  assert(_realLP != 0);
7507 
7508  bool scale = _realLP->isScaled();
7509  _realLP->changeLhs(i, lhs, scale);
7510 
7511  if( _isRealLPLoaded )
7512  {
7514  }
7515  else if( _hasBasis && _basisStatusRows[i] == SPxSolver::ON_LOWER && lhs <= -realParam(SoPlex::INFTY) )
7517 
7518  }
7519 
7520 
7521 
7522  /// changes right-hand side vector to \p rhs and adjusts basis
7524  {
7525  assert(_realLP != 0);
7526 
7527  bool scale = _realLP->isScaled();
7528  _realLP->changeRhs(rhs, scale);
7529 
7530  if( _isRealLPLoaded )
7531  {
7533  }
7534  else if( _hasBasis )
7535  {
7536  for( int i = numRowsReal() - 1; i >= 0; i-- )
7537  {
7540  }
7541  }
7542  }
7543 
7544 
7545 
7546  /// changes right-hand side of row \p i to \p rhs and adjusts basis
7547  void SoPlex::_changeRhsReal(int i, const Real& rhs)
7548  {
7549  assert(_realLP != 0);
7550 
7551  bool scale = _realLP->isScaled();
7552  _realLP->changeRhs(i, rhs, scale);
7553 
7554  if( _isRealLPLoaded )
7555  {
7557  }
7560  }
7561 
7562 
7563 
7564  /// changes left- and right-hand side vectors and adjusts basis
7565  void SoPlex::_changeRangeReal(const VectorReal& lhs, const VectorReal& rhs)
7566  {
7567  assert(_realLP != 0);
7568 
7569  bool scale = _realLP->isScaled();
7570  _realLP->changeRange(lhs, rhs, scale);
7571 
7572  if( _isRealLPLoaded )
7573  {
7575  }
7576  else if( _hasBasis )
7577  {
7578  for( int i = numRowsReal() - 1; i >= 0; i-- )
7579  {
7580  if( _basisStatusRows[i] == SPxSolver::ON_LOWER && lhs[i] <= -realParam(SoPlex::INFTY) )
7582  else if( _basisStatusRows[i] == SPxSolver::ON_UPPER && rhs[i] >= realParam(SoPlex::INFTY) )
7584  }
7585  }
7586  }
7587 
7588 
7589 
7590  /// changes left- and right-hand side of row \p i and adjusts basis
7591  void SoPlex::_changeRangeReal(int i, const Real& lhs, const Real& rhs)
7592  {
7593  assert(_realLP != 0);
7594 
7595  bool scale = _realLP->isScaled();
7596  _realLP->changeRange(i, lhs, rhs, scale);
7597 
7598  if( _isRealLPLoaded )
7599  {
7601  }
7602  else if( _hasBasis )
7603  {
7606  else if( _basisStatusRows[i] == SPxSolver::ON_UPPER && rhs >= realParam(SoPlex::INFTY) )
7608  }
7609  }
7610 
7611 
7612 
7613  /// replaces column \p i with \p lpcol and adjusts basis
7614  void SoPlex::_changeColReal(int i, const LPColReal& lpcol)
7615  {
7616  assert(_realLP != 0);
7617 
7618  bool scale = _realLP->isScaled();
7619  _realLP->changeCol(i, lpcol, scale);
7620 
7621  if( _isRealLPLoaded )
7622  {
7624  }
7625  else if( _hasBasis )
7626  {
7628  _hasBasis = false;
7629  else if( _basisStatusCols[i] == SPxSolver::ON_LOWER && lpcol.lower() <= -realParam(SoPlex::INFTY) )
7631  else if( _basisStatusCols[i] == SPxSolver::ON_UPPER && lpcol.upper() >= realParam(SoPlex::INFTY) )
7633  }
7634 
7636  }
7637 
7638 
7639 
7640  /// changes vector of lower bounds to \p lower and adjusts basis
7642  {
7643  assert(_realLP != 0);
7644 
7645  bool scale = _realLP->isScaled();
7646  _realLP->changeLower(lower, scale);
7647 
7648  if( _isRealLPLoaded )
7649  {
7651  }
7652  else if( _hasBasis )
7653  {
7654  for( int i = numColsReal() - 1; i >= 0; i-- )
7655  {
7656  if( _basisStatusCols[i] == SPxSolver::ON_LOWER && lower[i] <= -realParam(SoPlex::INFTY) )
7658  }
7659  }
7660  }
7661 
7662 
7663 
7664  /// changes lower bound of column i to \p lower and adjusts basis
7665  void SoPlex::_changeLowerReal(int i, const Real& lower)
7666  {
7667  assert(_realLP != 0);
7668 
7669  bool scale = _realLP->isScaled();
7670  _realLP->changeLower(i, lower, scale);
7671 
7672  if( _isRealLPLoaded )
7673  {
7675  }
7676  else if( _hasBasis && _basisStatusCols[i] == SPxSolver::ON_LOWER && lower <= -realParam(SoPlex::INFTY) )
7678  }
7679 
7680 
7681 
7682  /// changes vector of upper bounds to \p upper and adjusts basis
7684  {
7685  assert(_realLP != 0);
7686 
7687  bool scale = _realLP->isScaled();
7688  _realLP->changeUpper(upper, scale);
7689 
7690  if( _isRealLPLoaded )
7691  {
7693  }
7694  else if( _hasBasis )
7695  {
7696  for( int i = numColsReal() - 1; i >= 0; i-- )
7697  {
7698  if( _basisStatusCols[i] == SPxSolver::ON_UPPER && upper[i] >= realParam(SoPlex::INFTY) )
7700  }
7701  }
7702  }
7703 
7704 
7705 
7706  /// changes \p i 'th upper bound to \p upper and adjusts basis
7707  void SoPlex::_changeUpperReal(int i, const Real& upper)
7708  {
7709  assert(_realLP != 0);
7710 
7711  bool scale = _realLP->isScaled();
7712  _realLP->changeUpper(i, upper, scale);
7713 
7714  if( _isRealLPLoaded )
7715  {
7717  }
7718  else if( _hasBasis && _basisStatusCols[i] == SPxSolver::ON_UPPER && upper >= realParam(SoPlex::INFTY) )
7720  }
7721 
7722 
7723 
7724  /// changes vectors of column bounds to \p lower and \p upper and adjusts basis
7725  void SoPlex::_changeBoundsReal(const VectorReal& lower, const VectorReal& upper)
7726  {
7727  assert(_realLP != 0);
7728 
7729  bool scale = _realLP->isScaled();
7730  _realLP->changeBounds(lower, upper, scale);
7731 
7732  if( _isRealLPLoaded )
7733  {
7735  }
7736  else if( _hasBasis )
7737  {
7738  for( int i = numColsReal() - 1; i >= 0; i-- )
7739  {
7740  if( _basisStatusCols[i] == SPxSolver::ON_LOWER && lower[i] <= -realParam(SoPlex::INFTY) )
7742  else if( _basisStatusCols[i] == SPxSolver::ON_UPPER && upper[i] >= realParam(SoPlex::INFTY) )
7744  }
7745  }
7746  }
7747 
7748 
7749 
7750  /// changes bounds of column \p i to \p lower and \p upper and adjusts basis
7751  void SoPlex::_changeBoundsReal(int i, const Real& lower, const Real& upper)
7752  {
7753  assert(_realLP != 0);
7754 
7755  bool scale = _realLP->isScaled();
7756  _realLP->changeBounds(i, lower, upper, scale);
7757 
7758  if( _isRealLPLoaded )
7759  {
7761  }
7762  else if( _hasBasis )
7763  {
7766  else if( _basisStatusCols[i] == SPxSolver::ON_UPPER && upper >= realParam(SoPlex::INFTY) )
7768  }
7769  }
7770 
7771 
7772 
7773  /// changes matrix entry in row \p i and column \p j to \p val and adjusts basis
7774  void SoPlex::_changeElementReal(int i, int j, const Real& val)
7775  {
7776  assert(_realLP != 0);
7777 
7778  bool scale = _realLP->isScaled();
7779  _realLP->changeElement(i, j, val, scale);
7780 
7781  if( _isRealLPLoaded )
7782  {
7784  }
7785  else if( _hasBasis )
7786  {
7788  _hasBasis = false;
7789  }
7790 
7792  }
7793 
7794 
7795 
7796  /// removes row \p i and adjusts basis
7798  {
7799  assert(_realLP != 0);
7800 
7801  _realLP->removeRow(i);
7802 
7803  if( _isRealLPLoaded )
7804  {
7806  }
7807  else if( _hasBasis )
7808  {
7810  _hasBasis = false;
7811  else
7812  {
7815  }
7816  }
7817 
7819  }
7820 
7821 
7822 
7823  /// removes all rows with an index \p i such that \p perm[i] < 0; upon completion, \p perm[i] >= 0 indicates the
7824  /// new index where row \p i has been moved to; note that \p perm must point to an array of size at least
7825  /// #numRowsReal()
7826  void SoPlex::_removeRowsReal(int perm[])
7827  {
7828  assert(_realLP != 0);
7829 
7830  _realLP->removeRows(perm);
7831 
7832  if( _isRealLPLoaded )
7833  {
7835  }
7836  else if( _hasBasis )
7837  {
7838  for( int i = numRowsReal() - 1; i >= 0 && _hasBasis; i-- )
7839  {
7840  if( perm[i] < 0 && _basisStatusRows[i] != SPxSolver::BASIC )
7841  _hasBasis = false;
7842  else if( perm[i] >= 0 && perm[i] != i )
7843  {
7844  assert(perm[i] < numRowsReal());
7845  assert(perm[perm[i]] < 0);
7846 
7847  _basisStatusRows[perm[i]] = _basisStatusRows[i];
7848  }
7849  }
7850 
7851  if( _hasBasis )
7853  }
7854 
7856  }
7857 
7858 
7859 
7860  /// removes column i
7862  {
7863  assert(_realLP != 0);
7864 
7865  _realLP->removeCol(i);
7866 
7867  if( _isRealLPLoaded )
7868  {
7870  }
7871  else if( _hasBasis )
7872  {
7874  _hasBasis = false;
7875  else
7876  {
7879  }
7880  }
7881 
7883  }
7884 
7885 
7886 
7887  /// removes all columns with an index \p i such that \p perm[i] < 0; upon completion, \p perm[i] >= 0 indicates the
7888  /// new index where column \p i has been moved to; note that \p perm must point to an array of size at least
7889  /// #numColsReal()
7890  void SoPlex::_removeColsReal(int perm[])
7891  {
7892  assert(_realLP != 0);
7893 
7894  _realLP->removeCols(perm);
7895 
7896  if( _isRealLPLoaded )
7897  {
7899  }
7900  else if( _hasBasis )
7901  {
7902  for( int i = numColsReal() - 1; i >= 0 && _hasBasis; i-- )
7903  {
7904  if( perm[i] < 0 && _basisStatusCols[i] == SPxSolver::BASIC )
7905  _hasBasis = false;
7906  else if( perm[i] >= 0 && perm[i] != i )
7907  {
7908  assert(perm[i] < numColsReal());
7909  assert(perm[perm[i]] < 0);
7910 
7911  _basisStatusCols[perm[i]] = _basisStatusCols[i];
7912  }
7913  }
7914 
7915  if( _hasBasis )
7917  }
7918 
7920  }
7921 
7922 
7923 
7924  /// invalidates solution
7926  {
7927  ///@todo maybe this should be done individually at the places when this method is called
7929 
7930  _solReal.invalidate();
7931  _hasSolReal = false;
7932 
7934  _hasSolRational = false;
7935  }
7936 
7937 
7938 
7939  /// enables simplifier and scaler
7941  {
7942  // type of simplifier
7943  switch( intParam(SoPlex::SIMPLIFIER) )
7944  {
7945  case SIMPLIFIER_OFF:
7946  _simplifier = 0;
7947  break;
7948  case SIMPLIFIER_AUTO:
7950  assert(_simplifier != 0);
7952  break;
7953  default:
7954  break;
7955  }
7956 
7957  // type of scaler
7958  switch( intParam(SoPlex::SCALER) )
7959  {
7960  case SCALER_OFF:
7961  _scaler = 0;
7962  break;
7963  case SCALER_UNIEQUI:
7965  break;
7966  case SCALER_BIEQUI:
7968  break;
7969  case SCALER_GEO1:
7970  _scaler = &_scalerGeo1;
7971  break;
7972  case SCALER_GEO8:
7973  _scaler = &_scalerGeo8;
7974  break;
7975  case SCALER_LEASTSQ:
7977  break;
7978  case SCALER_GEOEQUI:
7980  break;
7981  default:
7982  break;
7983  }
7984  }
7985 
7986 
7987 
7988  /// disables simplifier and scaler
7990  {
7991  _simplifier = 0;
7992 
7993  // preserve scaler when persistent scaling is used
7994  if( !_isRealLPScaled )
7995  _scaler = 0;
7996  else
7998  }
7999 
8000 
8001 
8002  /// ensures that the rational LP is available; performs no sync
8004  {
8005  if( _rationalLP == 0 )
8006  {
8010  }
8011  }
8012 
8013 
8014 
8015  /// ensures that the real LP and the basis are loaded in the solver; performs no sync
8017  {
8018  if( !_isRealLPLoaded )
8019  {
8020  assert(_realLP != &_solver);
8021 
8023  _realLP->~SPxLPReal();
8024  spx_free(_realLP);
8025  _realLP = &_solver;
8026  _isRealLPLoaded = true;
8027 
8028  if( _hasBasis )
8029  {
8030  ///@todo this should not fail even if the basis is invalid (wrong dimension or wrong number of basic
8031  /// entries); fix either in SPxSolver or in SPxBasis
8032  assert(_basisStatusRows.size() == numRowsReal());
8033  assert(_basisStatusCols.size() == numColsReal());
8036  }
8037  }
8038  }
8039 
8040 
8041 
8042  /// call floating-point solver and update statistics on iterations etc.
8044  {
8045  bool _hadBasis = _hasBasis;
8046 
8047  // set time and iteration limit
8050  else
8054  else
8056 
8057  // ensure that tolerances are not too small
8058  if( _solver.feastol() < 1e-12 )
8059  _solver.setFeastol(1e-12);
8060  if( _solver.opttol() < 1e-12 )
8061  _solver.setOpttol(1e-12);
8062 
8063  // set correct representation
8066  && _solver.rep() != SPxSolver::COLUMN )
8067  {
8069  }
8072  &&_solver.rep() != SPxSolver::ROW )
8073  {
8075  }
8076 
8077  // set correct type
8080  && _solver.type() != SPxSolver::ENTER )
8081  {
8083  }
8086  && _solver.type() != SPxSolver::LEAVE )
8087  {
8089  }
8090 
8091  // set pricing modes
8096  _solver.hyperPricing(true);
8098  _solver.hyperPricing(false);
8099 
8103 
8104  // call floating-point solver and catch exceptions
8106  try
8107  {
8108  _solver.solve();
8109  }
8110  catch( const SPxException& E )
8111  {
8112  MSG_INFO1( spxout, spxout << "Caught exception <" << E.what() << "> while solving real LP.\n" );
8114  }
8115  catch( ... )
8116  {
8117  MSG_INFO1( spxout, spxout << "Caught unknown exception while solving real LP.\n" );
8119  }
8121 
8122  // invalidate rational factorization of basis if pivots have been performed
8123  if( _solver.iterations() > 0 )
8125 
8126  // record statistics
8129  _statistics->iterationsFromBasis += _hadBasis ? _solver.iterations() : 0;
8137 
8142  }
8143 
8144 
8145 
8146  /// reads real LP in LP or MPS format from file and returns true on success; gets row names, column names, and
8147  /// integer variables if desired
8148  bool SoPlex::_readFileReal(const char* filename, NameSet* rowNames, NameSet* colNames, DIdxSet* intVars)
8149  {
8150  assert(_realLP != 0);
8151 
8152  // clear statistics
8154 
8155  // update status
8156  clearBasis();
8159 
8160  // start timing
8162 
8163  // read
8164  bool success = _realLP->readFile(filename, rowNames, colNames, intVars);
8165 
8166  // stop timing
8168 
8169  if( success )
8170  {
8173 
8174  // if sync mode is auto, we have to copy the (rounded) real LP to the rational LP; this is counted to sync time
8175  // and not to reading time
8177  _syncLPRational();
8178  }
8179  else
8180  clearLPReal();
8181 
8182  return success;
8183  }
8184 
8185 
8186 
8187  /// reads rational LP in LP or MPS format from file and returns true on success; gets row names, column names, and
8188  /// integer variables if desired
8189  bool SoPlex::_readFileRational(const char* filename, NameSet* rowNames, NameSet* colNames, DIdxSet* intVars)
8190  {
8191  // clear statistics
8193 
8194  // start timing
8196 
8197  // update status
8198  clearBasis();
8201 
8202  // read
8204  bool success = _rationalLP->readFile(filename, rowNames, colNames, intVars);
8205 
8206  // stop timing
8208 
8209  if( success )
8210  {
8214 
8215  // if sync mode is auto, we have to copy the (rounded) real LP to the rational LP; this is counted to sync time
8216  // and not to reading time
8218  _syncLPReal();
8219  // if a rational LP file is read, but only the (rounded) real LP should be kept, we have to free the rational LP
8221  {
8222  _syncLPReal();
8223  _rationalLP->~SPxLPRational();
8225  }
8226  }
8227  else
8228  clearLPRational();
8229 
8230  return success;
8231  }
8232 
8233 
8234 
8235  /// completes range type arrays after adding columns and/or rows
8237  {
8238  // we use one method for bot columns and rows, because during column/row addition, rows/columns can be added
8239  // implicitly
8240  for( int i = _colTypes.size(); i < numColsRational(); i++ )
8242  for( int i = _rowTypes.size(); i < numRowsRational(); i++ )
8244  }
8245 
8246 
8247 
8248  /// recomputes range types from scratch using real LP
8250  {
8252  for( int i = 0; i < numRowsReal(); i++ )
8253  _rowTypes[i] = _rangeTypeReal(_realLP->lhs(i), _realLP->rhs(i));
8255  for( int i = 0; i < numColsReal(); i++ )
8257  }
8258 
8259 
8260 
8261  /// recomputes range types from scratch using rational LP
8263  {
8265  for( int i = 0; i < numRowsRational(); i++ )
8268  for( int i = 0; i < numColsRational(); i++ )
8270  }
8271 
8272 
8273 
8274  /// synchronizes real LP with rational LP, i.e., copies (rounded) rational LP into real LP, without looking at the sync mode
8275  void SoPlex::_syncLPReal(bool time)
8276  {
8277  // start timing
8278  if( time )
8280 
8281  // copy LP
8282  if( _isRealLPLoaded )
8284  else
8285  *_realLP = *_rationalLP;
8286 
8287  ///@todo try loading old basis
8288  _hasBasis = false;
8290 
8291  // stop timing
8292  if( time )
8294  }
8295 
8296 
8297 
8298  /// synchronizes rational LP with real LP, i.e., copies real LP to rational LP, without looking at the sync mode
8299  void SoPlex::_syncLPRational(bool time)
8300  {
8301  // start timing
8302  if( time )
8304 
8305  // copy LP
8307  *_rationalLP = *_realLP;
8309 
8310  // stop timing
8311  if( time )
8313  }
8314 
8315 
8316 
8317  /// synchronizes rational solution with real solution, i.e., copies (rounded) rational solution to real solution
8319  {
8320  if( _hasSolRational && !_hasSolReal )
8321  {
8323  _hasSolReal = true;
8324  }
8325  }
8326 
8327 
8328 
8329  /// synchronizes real solution with rational solution, i.e., copies real solution to rational solution
8331  {
8332  if( _hasSolReal && !_hasSolRational )
8333  {
8335  _hasSolRational = true;
8336  }
8337  }
8338 
8339 
8340 
8341  /// returns pointer to a constant unit vector available until destruction of the SoPlex class
8343  {
8344  assert(i >= 0);
8345 
8346  if( i < 0 )
8347  return 0;
8348  else if( i >= _unitMatrixRational.size() )
8349  _unitMatrixRational.append(i + 1 - _unitMatrixRational.size(), (UnitVectorRational*)0);
8350  assert(i < _unitMatrixRational.size());
8351 
8352  if( _unitMatrixRational[i] == 0 )
8353  {
8356  }
8357  assert(_unitMatrixRational[i] != 0);
8358 
8359  return _unitMatrixRational[i];
8360  }
8361 
8362 
8363 
8364  /// parses one line in a settings file and returns true on success; note that the string is modified
8365  bool SoPlex::_parseSettingsLine(char* line, const int lineNumber)
8366  {
8367  assert(line != 0);
8368 
8369  // find the start of the parameter type
8370  while( *line == ' ' || *line == '\t' || *line == '\r' )
8371  line++;
8372  if( *line == '\0' || *line == '\n' || *line == '#' )
8373  return true;
8374  char* paramTypeString = line;
8375 
8376  // find the end of the parameter type
8377  while( *line != ' ' && *line != '\t' && *line != '\r' && *line != '\n' && *line != '#' && *line != '\0' && *line != ':' )
8378  line++;
8379  if( *line == ':' )
8380  {
8381  *line = '\0';
8382  line++;
8383  }
8384  else
8385  {
8386  *line = '\0';
8387  line++;
8388 
8389  // search for the ':' char in the line
8390  while( *line == ' ' || *line == '\t' || *line == '\r' )
8391  line++;
8392  if( *line != ':' )
8393  {
8394  MSG_INFO1( spxout, spxout << "Error parsing settings file: no ':' separating parameter type and name in line " << lineNumber << ".\n" );
8395  return false;
8396  }
8397  line++;
8398  }
8399 
8400  // find the start of the parameter name
8401  while( *line == ' ' || *line == '\t' || *line == '\r' )
8402  line++;
8403  if( *line == '\0' || *line == '\n' || *line == '#' )
8404  {
8405  MSG_INFO1( spxout, spxout << "Error parsing settings file: no parameter name in line " << lineNumber << ".\n");
8406  return false;
8407  }
8408  char* paramName = line;
8409 
8410  // find the end of the parameter name
8411  while( *line != ' ' && *line != '\t' && *line != '\r' && *line != '\n' && *line != '#' && *line != '\0' && *line != '=' )
8412  line++;
8413  if( *line == '=' )
8414  {
8415  *line = '\0';
8416  line++;
8417  }
8418  else
8419  {
8420  *line = '\0';
8421  line++;
8422 
8423  // search for the '=' char in the line
8424  while( *line == ' ' || *line == '\t' || *line == '\r' )
8425  line++;
8426  if( *line != '=' )
8427  {
8428  MSG_INFO1( spxout, spxout << "Error parsing settings file: no '=' after parameter name in line " << lineNumber << ".\n" );
8429  return false;
8430  }
8431  line++;
8432  }
8433 
8434  // find the start of the parameter value string
8435  while( *line == ' ' || *line == '\t' || *line == '\r' )
8436  line++;
8437  if( *line == '\0' || *line == '\n' || *line == '#' )
8438  {
8439  MSG_INFO1( spxout, spxout << "Error parsing settings file: no parameter value in line " << lineNumber << ".\n");
8440  return false;
8441  }
8442  char* paramValueString = line;
8443 
8444  // find the end of the parameter value string
8445  while( *line != ' ' && *line != '\t' && *line != '\r' && *line != '\n' && *line != '#' && *line != '\0' )
8446  line++;
8447  if( *line != '\0' )
8448  {
8449  // check, if the rest of the line is clean
8450  *line = '\0';
8451  line++;
8452  while( *line == ' ' || *line == '\t' || *line == '\r' )
8453  line++;
8454  if( *line != '\0' && *line != '\n' && *line != '#' )
8455  {
8456  MSG_INFO1( spxout, spxout << "Error parsing settings file: additional character '" << *line << "' after parameter value in line " << lineNumber << ".\n" );
8457  return false;
8458  }
8459  }
8460 
8461  // check whether we have a bool parameter
8462  if( strncmp(paramTypeString, "bool", 4) == 0 )
8463  {
8464  for( int param = 0; ; param++ )
8465  {
8466  if( param >= SoPlex::BOOLPARAM_COUNT )
8467  {
8468  MSG_INFO1( spxout, spxout << "Error parsing settings file: unknown parameter name <" << paramName << "> in line " << lineNumber << ".\n" );
8469  return false;
8470  }
8471  else if( strncmp(paramName, _currentSettings->boolParam.name[param].c_str(), SET_MAX_LINE_LEN) == 0 )
8472  {
8473  if( strncasecmp(paramValueString, "true", 4) == 0
8474  || strncasecmp(paramValueString, "TRUE", 4) == 0
8475  || strncasecmp(paramValueString, "t", 4) == 0
8476  || strncasecmp(paramValueString, "T", 4) == 0
8477  || strtol(paramValueString, NULL, 4) == 1 )
8478  {
8479  setBoolParam((SoPlex::BoolParam)param, true);
8480  break;
8481  }
8482  else if( strncasecmp(paramValueString, "false", 5) == 0
8483  || strncasecmp(paramValueString, "FALSE", 5) == 0
8484  || strncasecmp(paramValueString, "f", 5) == 0
8485  || strncasecmp(paramValueString, "F", 5) == 0
8486  || strtol(paramValueString, NULL, 5) == 0 )
8487  {
8488  setBoolParam((SoPlex::BoolParam)param, false);
8489  break;
8490  }
8491  else
8492  {
8493  MSG_INFO1( spxout, spxout << "Error parsing settings file: invalid value <" << paramValueString << "> for bool parameter <" << paramName << "> in line " << lineNumber << ".\n" );
8494  return false;
8495  }
8496  }
8497  }
8498 
8499  return true;
8500  }
8501 
8502  // check whether we have an integer parameter
8503  if( strncmp(paramTypeString, "int", 3) == 0 )
8504  {
8505  for( int param = 0; ; param++ )
8506  {
8507  if( param >= SoPlex::INTPARAM_COUNT )
8508  {
8509  MSG_INFO1( spxout, spxout << "Error parsing settings file: unknown parameter name <" << paramName << "> in line " << lineNumber << ".\n" );
8510  return false;
8511  }
8512  else if( strncmp(paramName, _currentSettings->intParam.name[param].c_str(), SET_MAX_LINE_LEN) == 0 )
8513  {
8514  int value;
8515 
8516  if( sscanf(paramValueString, "%d", &value) == 1 && setIntParam((SoPlex::IntParam)param, value, false) )
8517  break;
8518  else
8519  {
8520  MSG_INFO1( spxout, spxout << "Error parsing settings file: invalid value <" << paramValueString << "> for int parameter <" << paramName << "> in line " << lineNumber << ".\n" );
8521  return false;
8522  }
8523  }
8524  }
8525 
8526  return true;
8527  }
8528 
8529  // check whether we have a real parameter
8530  if( strncmp(paramTypeString, "real", 4) == 0 )
8531  {
8532  for( int param = 0; ; param++ )
8533  {
8534  if( param >= SoPlex::REALPARAM_COUNT )
8535  {
8536  MSG_INFO1( spxout, spxout << "Error parsing settings file: unknown parameter name <" << paramName << "> in line " << lineNumber << ".\n" );
8537  return false;
8538  }
8539  else if( strncmp(paramName, _currentSettings->realParam.name[param].c_str(), SET_MAX_LINE_LEN) == 0 )
8540  {
8541  Real value;
8542 
8543  if( sscanf(paramValueString, "%" REAL_FORMAT, &value) == 1 && setRealParam((SoPlex::RealParam)param, value) )
8544  break;
8545  else
8546  {
8547  MSG_INFO1( spxout, spxout << "Error parsing settings file: invalid value <" << paramValueString << "> for real parameter <" << paramName << "> in line " << lineNumber << ".\n" );
8548  return false;
8549  }
8550  }
8551  }
8552 
8553  return true;
8554  }
8555 
8556 #ifdef SOPLEX_WITH_RATIONALPARAM
8557  // check whether we have a rational parameter
8558  if( strncmp(paramTypeString, "rational", 8) == 0 )
8559  {
8560  for( int param = 0; ; param++ )
8561  {
8562  if( param >= SoPlex::RATIONALPARAM_COUNT )
8563  {
8564  MSG_INFO1( spxout, spxout << "Error parsing settings file: unknown parameter name <" << paramName << "> in line " << lineNumber << ".\n" );
8565  return false;
8566  }
8567  else if( strncmp(paramName, _currentSettings->rationalParam.name[param].c_str(), SET_MAX_LINE_LEN) == 0 )
8568  {
8569  Rational value;
8570 
8571  if( readStringRational(paramValueString, value) && setRationalParam((SoPlex::RationalParam)param, value) )
8572  break;
8573  else
8574  {
8575  MSG_INFO1( spxout, spxout << "Error parsing settings file: invalid value <" << paramValueString << "> for rational parameter <" << paramName << "> in line " << lineNumber << ".\n" );
8576  return false;
8577  }
8578  }
8579  }
8580 
8581  return true;
8582  }
8583 #endif
8584 
8585  // check whether we have the random seed
8586  if( strncmp(paramTypeString, "uint", 4) == 0 )
8587  {
8588  if( strncmp(paramName, "random_seed", 11) == 0 )
8589  {
8590  unsigned int value;
8591  char format[SPX_MAXSTRLEN];
8592  spxSnprintf(format, sizeof(format), "%%%du", (int) sizeof(value)-1);
8593 
8594  if( sscanf(paramValueString, format, &value) == 1 )
8595  {
8596  setRandomSeed(value);
8597  return true;
8598  }
8599  }
8600 
8601  MSG_INFO1( spxout, spxout << "Error parsing settings file for uint parameter <random_seed>.\n" );
8602  return false;
8603  }
8604 
8605  MSG_INFO1( spxout, spxout << "Error parsing settings file: invalid parameter type <" << paramTypeString << "> for parameter <" << paramName << "> in line " << lineNumber << ".\n" );
8606 
8607  return false;
8608  }
8609 } // namespace soplex
8610 #endif
const VectorBase< R > & rhs() const
Returns right hand side vector.
Definition: spxlpbase.h:219
void changeLhsRational(const VectorRational &lhs)
changes left-hand side vector for constraints to lhs
Definition: soplex.cpp:2102
virtual void buildDualProblem(SPxLPBase< R > &dualLP, SPxRowId primalRowIds[]=0, SPxColId primalColIds[]=0, SPxRowId dualRowIds[]=0, SPxColId dualColIds[]=0, int *nprimalrows=0, int *nprimalcols=0, int *ndualrows=0, int *ndualcols=0)
Building the dual problem from a given LP.
int _lastSolveMode
Definition: soplex.h:1813
const VectorRational & rhsRational() const
returns right-hand side vector
Definition: soplex.cpp:1161
floating-point check
Definition: soplex.h:1222
bool isNotZero(Real a, Real eps=Param::epsilon())
returns true iff |a| > eps
Definition: spxdefines.h:422
RangeType
type of bounds and sides
Definition: soplex.h:1645
SPxLPBase< Real > SPxLPReal
Definition: spxlp.h:36
const char * getRatiotesterName()
name of currently loaded ratiotester
Definition: soplex.cpp:5109
DVectorBase< R > _slacks
Definition: solbase.h:219
textbook ratio test without stabilization
Definition: soplex.h:1170
void getRowsRational(int start, int end, LPRowSetRational &lprowset) const
gets rows start, ..., end.
Definition: soplex.cpp:1143
const VectorReal & maxObjRealInternal() const
returns objective function vector after transformation to a maximization problem; since this is how i...
Definition: soplex.cpp:1037
void _computeBasisInverseRational()
computes rational inverse of basis matrix as defined by _rationalLUSolverBind
int getSolveCount() const
number of solves performed
Definition: slufactor.h:263
bool multBasisTranspose(Real *vec, bool unscale=true)
multiply with transpose of basis matrix; vec * B^T (inplace)
Definition: soplex.cpp:4770
void _changeUpperReal(const VectorReal &upper)
changes vector of upper bounds to upper and adjusts basis
Definition: soplex.cpp:7683
bool getDual(VectorBase< R > &vector) const
gets the dual solution vector; returns true on success
Definition: solbase.h:94
void getRhsUnscaled(VectorBase< Real > &vec) const
Gets unscaled right hand side vector.
accuracy of conjugate gradient method in least squares scaling (higher value leads to more iterations...
Definition: soplex.h:1340
Vector & multWithBase(Vector &x) const
Vector-basis product.
Definition: spxbasis.cpp:940
virtual void removeRow(int i)
Removes i &#39;th row.
Definition: spxlpbase.h:904
int iterations() const
get number of iterations of current solution.
Definition: spxsolver.h:2091
zero tolerance used in factorization
Definition: soplex.h:1283
void getRow(int i, LPRowBase< R > &row) const
Gets i &#39;th row.
Definition: spxlpbase.h:180
void getUpperReal(DVectorReal &upper) const
gets upper bound vector
Definition: soplex.cpp:981
Rational _rationalMaxscaleincr
Definition: soplex.h:1561
Basis is dual feasible.
Definition: spxbasis.h:95
free variable fixed to zero.
Definition: spxsolver.h:194
int totalSizeDual(const int base=2) const
returns total size of dual solution
Definition: solbase.h:139
#define DEFAULT_EPS_FACTOR
Definition: spxdefines.h:233
void printVersion() const
prints version and compilation options
Definition: soplex.cpp:6856
SoPlex()
default constructor
Definition: soplex.cpp:559
not initialised error
Definition: spxsolver.h:208
bool getDualViolationRational(Rational &maxviol, Rational &sumviol)
gets violation of dual multipliers; returns true on success
Definition: soplex.cpp:3558
bool GE(Real a, Real b, Real eps=Param::epsilon())
returns true iff a >= b + eps
Definition: spxdefines.h:410
void printSolutionStatistics(std::ostream &os)
prints solution statistics
Definition: soplex.cpp:6668
refactor threshold for memory growth in factorization since last refactorization
Definition: soplex.h:1337
DVectorBase< R > _dualFarkas
Definition: solbase.h:223
Timer * syncTime
time for synchronization between real and rational LP (included in solving time)
Definition: statistics.h:92
void setRep(Representation p_rep)
switch to ROW or COLUMN representation if not already used.
Definition: spxsolver.cpp:256
Basis is not known to be dual nor primal feasible.
Definition: spxbasis.h:94
No matrix has yet been loaded.
void coSolve(Vector &x, const Vector &rhs)
Cosolves linear system with basis matrix.
Definition: spxbasis.h:719
bool getDualNorms(int &nnormsRow, int &nnormsCol, Real *norms) const
gets steepest edge norms and returns false if they are not available
Definition: soplex.cpp:1064
const VectorBase< R > & lower() const
Definition: lpcolsetbase.h:130
void _addColReal(const LPColReal &lpcol)
adds a single column to the real LP and adjusts basis
Definition: soplex.cpp:7387
int numRowsReal() const
returns number of rows
Definition: soplex.cpp:797
bool getBasisInverseRowReal(int r, Real *coef, int *inds=NULL, int *ninds=NULL, bool unscale=true)
computes row r of basis inverse; returns true on success
Definition: soplex.cpp:4104
Rational minAbsNonzeroRational() const
returns smallest non-zero element in absolute value
Definition: soplex.cpp:1116
static void setEpsilon(Real eps)
Definition: spxdefines.cpp:50
void removeRowsRational(int perm[])
removes all rows with an index i such that perm[i] < 0; upon completion, perm[i] >= 0 indicates the n...
Definition: soplex.cpp:2604
type of starter used to create crash basis
Definition: soplex.h:974
void removeColsReal(int perm[])
removes all columns with an index i such that perm[i] < 0; upon completion, perm[i] >= 0 indicates th...
Definition: soplex.cpp:1814
bool getDualNorms(int &nnormsRow, int &nnormsCol, Real *norms) const
get dual norms
Definition: spxsolver.cpp:1982
The time limit has been hit.
const VectorBase< R > & upper() const
Returns upper bound vector.
Definition: spxlpbase.h:456
void _optimizeReal()
solves real LP
Definition: solvereal.cpp:29
const Settings & settings() const
returns current parameter settings
Definition: soplex.cpp:5570
upper limit on objective value
Definition: soplex.h:1301
void getNdualNorms(int &nnormsRow, int &nnormsCol) const
get number of dual norms
Definition: spxsolver.cpp:1957
void _changeElementReal(int i, int j, const Real &val)
changes matrix entry in row i and column j to val and adjusts basis
Definition: soplex.cpp:7774
virtual R minAbsNzo(bool unscaled=true) const
Absolute smallest non-zero element in (possibly scaled) LP.
THREADLOCAL const Real infinity
Definition: spxdefines.cpp:26
general zero tolerance
Definition: soplex.h:1280
void getRows(int start, int end, LPRowSetBase< R > &set) const
Gets rows start, ... end.
Definition: spxlpbase.h:195
mode for solution polishing
Definition: soplex.h:1007
void setOutstream(SPxOut &newOutstream)
Definition: spxlpbase.h:125
Real _realParamValues[SoPlex::REALPARAM_COUNT]
array of current real parameter values
Definition: soplex.h:1427
void _changeRangeReal(const VectorReal &lhs, const VectorReal &rhs)
changes left- and right-hand side vectors and adjusts basis
Definition: soplex.cpp:7565
const SPxRatioTester * ratiotester() const
return loaded SPxRatioTester.
Definition: spxsolver.h:1756
type of ratio test
Definition: soplex.h:980
void removeColReal(int i)
removes column i
Definition: soplex.cpp:1788
maximum increase of scaling factors between refinements
Definition: soplex.h:1310
virtual void getRowUnscaled(const SPxLPBase< Real > &lp, int i, DSVector &vec) const
returns unscaled row i
Definition: spxscaler.cpp:460
SPxMainSM _simplifierMainSM
Definition: soplex.h:1571
Real maxAbsNonzeroReal() const
returns biggest non-zero element in absolute value
Definition: soplex.cpp:833
verbosity level
Definition: soplex.h:965
continue iterative refinement with exact basic solution if not optimal?
Definition: soplex.h:919
void setBasis(const VarStatus rows[], const VarStatus cols[])
set the lp solver&#39;s basis.
Definition: spxsolver.cpp:1873
const SVectorReal & colVectorRealInternal(int i) const
returns vector of col i, ignoring scaling
Definition: soplex.cpp:945
type of timer
Definition: soplex.h:995
void setMaxUpdates(int maxUp)
change maximum number of iterations until a refactorization is performed
Definition: spxbasis.h:450
int spxSnprintf(char *t, int len, const char *s,...)
safe version of snprintf
Definition: spxdefines.h:464
void resetCounters()
reset timers and counters
Definition: slufactor.h:268
Read MPS format files.
number of real parameters
Definition: soplex.h:1346
apply standard floating-point algorithm
Definition: soplex.h:1209
type of computational form, i.e., column or row representation
Definition: soplex.h:941
int stallRefinements
number of refinement steps without pivots
Definition: statistics.h:111
int totalSizePrimal(const int base=2) const
returns total size of primal solution
Definition: solbase.h:125
void changeColRational(int i, const LPColRational &lpcol)
replaces column i with lpcol
Definition: soplex.cpp:2285
bool getBasisIndRational(DataArray< int > &bind)
gets an array of indices for the columns of the rational basis matrix; bind[i] >= 0 means that the i-...
Definition: soplex.cpp:4906
bool getPrimalReal(VectorReal &vector)
gets the primal solution vector if available; returns true on success
Definition: soplex.cpp:2973
T * get_ptr()
get a C pointer to the data.
Definition: dataarray.h:110
void reMax(int newmax=0)
resets max() to newmax.
Definition: nameset.cpp:138
int size() const
Number of used indices.
Definition: svectorbase.h:152
equilibrium scaling on rows or columns
Definition: soplex.h:1110
pivot zero tolerance used in factorization
Definition: soplex.h:1289
int numRowsRational() const
returns number of rows
Definition: soplex.cpp:1089
bool writeDualFileReal(const char *filename, const NameSet *rowNames=0, const NameSet *colNames=0, const DIdxSet *intvars=0) const
writes the dual of the real LP to file; LP or MPS format is chosen from the extension in filename; if...
Definition: soplex.cpp:5181
objective offset
Definition: soplex.h:1343
bool getDualRational(VectorRational &vector)
gets the dual solution vector if available; returns true on success
Definition: soplex.cpp:3328
refinement limit (-1 if unlimited)
Definition: soplex.h:956
void setSolutionPolishing(SolutionPolish _polishObj)
set objective of solution polishing (0: off, 1: max_basic_slack, 2: min_basic_slack) ...
Definition: spxsolver.h:616
class of parameter settings
Definition: soplex.h:1359
SPxLPRational * _rationalLP
Definition: soplex.h:1616
void printShortStatistics(std::ostream &os)
prints short statistics
Definition: soplex.cpp:6754
Status getBasis(VarStatus rows[], VarStatus cols[], const int rowsSize=-1, const int colsSize=-1) const
get current basis, and return solver status.
Definition: spxsolver.cpp:1800
Real coefReal(int row, int col) const
returns (unscaled) coefficient
Definition: soplex.cpp:842
bool getSlacksRational(VectorRational &vector)
gets the vector of slack values if available; returns true on success
Definition: soplex.cpp:3298
standard Harris ratio test
Definition: soplex.h:1173
minimize number of basic slack variables, i.e. more variables in between bounds
Definition: spxsolver.h:231
bool multBasis(Real *vec, bool unscale=true)
multiply with basis matrix; B * vec (inplace)
Definition: soplex.cpp:4660
void getColsRational(int start, int end, LPColSetRational &lpcolset) const
gets columns start, ..., end
Definition: soplex.cpp:1215
bool getSlacks(VectorBase< R > &vector) const
gets the vector of slack values; returns true on success
Definition: solbase.h:65
int totalSizePrimalRational(const int base=2)
get size of primal solution
Definition: soplex.cpp:3764
void _addColsReal(const LPColSetReal &lpcolset)
adds multiple columns to the real LP and adjusts basis
Definition: soplex.cpp:7430
Basis is optimal, i.e. dual and primal feasible.
Definition: spxbasis.h:97
Real feastol() const
allowed primal feasibility tolerance.
Definition: spxsolver.h:786
unsigned int randomSeed() const
returns the current random seed of the solver instance
Definition: soplex.cpp:7163
virtual void setBasisSolver(SLinSolver *slu, const bool destroy=false)
setup linear solver to use. If destroy is true, slusolver will be freed in destructor.
Definition: spxsolver.cpp:83
Real sumDualDegeneracy()
get the sum of dual degeneracy
Definition: spxsolver.h:2079
time limit in seconds (INFTY if unlimited)
Definition: soplex.h:1295
mode for iterative refinement strategy
Definition: soplex.h:989
SPxGeometSC _scalerGeo8
Definition: soplex.h:1575
void changeRangeReal(const VectorReal &lhs, const VectorReal &rhs)
changes left- and right-hand side vectors
Definition: soplex.cpp:1482
virtual bool readFile(const char *filename, NameSet *rowNames=0, NameSet *colNames=0, DIdxSet *intVars=0)
Reads LP from a file.
Definition: spxlpbase.h:1154
Rational _rationalFeastol
Definition: soplex.h:1559
void writeStateReal(const char *filename, const NameSet *rowNames=0, const NameSet *colNames=0, const bool cpxFormat=false) const
writes internal LP, basis information, and parameter settings; if rowNames and colNames are NULL...
Definition: soplex.cpp:5487
DVectorBase< R > _primalRay
Definition: solbase.h:220
bool isScaled() const
Returns true if and only if the LP is scaled.
Definition: spxlpbase.h:139
void setUtype(UpdateType tp)
sets update type.
Definition: slufactor.h:122
R rhsUnscaled(int i) const
Returns unscaled right hand side of row number i.
void _removeColsReal(int perm[])
removes all columns with an index i such that perm[i] < 0; upon completion, perm[i] >= 0 indicates th...
Definition: soplex.cpp:7890
modified Harris ratio test
Definition: soplex.h:1176
virtual void changeCol(int n, const LPColBase< R > &newCol, bool scale=false)
Replaces i &#39;th column of LP with newCol. scale determines whether the new data should be scaled...
Definition: spxlpbase.h:1612
virtual ~SoPlex()
destructor
Definition: soplex.cpp:756
virtual void removeCols(int perm[])
Removes multiple columns.
Definition: spxlpbase.h:1020
bool getRedCostRational(VectorRational &vector)
gets the vector of reduced cost values if available; returns true on success
Definition: soplex.cpp:3343
bool LE(Real a, Real b, Real eps=Param::epsilon())
returns true iff a <= b + eps
Definition: spxdefines.h:398
DVectorBase< R > _redCost
Definition: solbase.h:222
int _unscaleCalls
Definition: soplex.h:1832
crash basis from a greedy solution
Definition: soplex.h:1138
Real getFactorTime() const
time spent in factorizations
Definition: slufactor.h:238
primal feasibility tolerance
Definition: soplex.h:1274
static struct soplex::SoPlex::Settings::RealParam realParam
Definition: soplex.cpp:553
void getObj(VectorBase< R > &pobj) const
Gets objective vector.
Definition: spxlpbase.h:394
bool LT(Real a, Real b, Real eps=Param::epsilon())
returns true iff a < b + eps
Definition: spxdefines.h:392
standard verbosity level
Definition: soplex.h:1084
void setType(Type tp)
set LEAVE or ENTER algorithm.
Definition: spxsolver.cpp:169
bound flipping ratio test for long steps in the dual simplex
Definition: soplex.h:1179
void setFillFactor(Real f)
set refactor threshold for fill-in in current factor update compared to fill-in in last factorization...
Definition: spxsolver.h:454
bool writeBasisFile(const char *filename, const NameSet *rowNames=0, const NameSet *colNames=0, const bool cpxFormat=false) const
writes basis information to filename; if rowNames and colNames are NULL, default names are used; retu...
Definition: soplex.cpp:5389
void _addRowReal(const LPRowReal &lprow)
adds a single row to the real LP and adjusts basis
Definition: soplex.cpp:7334
bool defaultValue[SoPlex::BOOLPARAM_COUNT]
array of default values for boolean parameters
Definition: soplex.h:1370
solve() aborted due to iteration limit.
Definition: spxsolver.h:213
R rhs() const
Right-hand side value.
Definition: lprowbase.h:215
SPxScaler * _scaler
Definition: soplex.h:1595
std::string name[SoPlex::BOOLPARAM_COUNT]
array of names for boolean parameters
Definition: soplex.h:1366
cpu or user time
Definition: soplex.h:1238
#define SOPLEX_VERSION
Definition: spxdefines.h:45
bool readBasisFile(const char *filename, const NameSet *rowNames=0, const NameSet *colNames=0)
reads basis information from filename and returns true on success; if rowNames and colNames are NULL...
Definition: soplex.cpp:5196
void changeRangeRational(const VectorRational &lhs, const VectorRational &rhs)
changes left- and right-hand side vectors
Definition: soplex.cpp:2225
mode for reading LP files
Definition: soplex.h:986
mode for synchronizing real and rational LP
Definition: soplex.h:983
void _syncLPReal(bool time=true)
synchronizes real LP with rational LP, i.e., copies (rounded) rational LP into real LP...
Definition: soplex.cpp:8275
bool hasDualFarkas() const
is a dual farkas ray available?
Definition: solbase.h:110
void _optimizeRational()
solves rational LP
No Problem has been loaded.
Definition: spxsolver.h:216
bool getDualFarkasReal(VectorReal &vector)
gets the Farkas proof if available; returns true on success
Definition: soplex.cpp:3048
void resetSettings(const bool quiet=false, const bool init=true)
resets default parameter settings
Definition: soplex.cpp:6198
automatic sync of real and rational LP
Definition: soplex.h:1189
void setValue(int i, R x)
Sets i &#39;th element to x.
Definition: ssvectorbase.h:218
void _recomputeRangeTypesRational()
recomputes range types from scratch using rational LP
Definition: soplex.cpp:8262
void syntaxError()
Definition: mpsinput.h:198
iteration limit (-1 if unlimited)
Definition: soplex.h:953
int number(const SPxRowId &id) const
Returns the row number of the row with identifier id.
Definition: spxlpbase.h:522
void changeObjReal(const VectorReal &obj)
changes objective function vector to obj
Definition: soplex.cpp:1649
void changeRowRational(int i, const LPRowRational &lprow)
replaces row i with lprow
Definition: soplex.cpp:2082
bool getRowViolationReal(Real &maxviol, Real &sumviol)
gets violation of constraints; returns true on success
Definition: soplex.cpp:3102
SPxFastRT _ratiotesterFast
Definition: soplex.h:1589
should cycling solutions be accepted during iterative refinement?
Definition: soplex.h:910
void _disableSimplifierAndScaler()
disables simplifier and scaler
Definition: soplex.cpp:7989
bool getRowViolationRational(Rational &maxviol, Rational &sumviol)
gets violation of constraints; returns true on success
Definition: soplex.cpp:3424
static struct soplex::SoPlex::Settings::IntParam intParam
Definition: soplex.cpp:552
should the decomposition based dual simplex be used to solve the LP? Setting this to true forces the ...
Definition: soplex.h:898
void add(const LPColBase< R > &pcol)
Definition: lpcolsetbase.h:255
Real lowerReal(int i) const
returns lower bound of column i
Definition: soplex.cpp:999
#define DEFAULT_INFINITY
Definition: spxdefines.h:241
bool getBasisInverseRowRational(const int r, SSVectorRational &vec)
computes row r of basis inverse; performs rational factorization if not available; returns true on su...
Definition: soplex.cpp:4922
NameSet * _rowNames
Definition: soplex.h:1777
Vector & multBaseWith(Vector &x) const
Basis-vector product.
Definition: spxbasis.cpp:979
void _removeRowReal(int i)
removes row i and adjusts basis
Definition: soplex.cpp:7797
lower bound is finite, upper bound is infinite
Definition: soplex.h:1651
bool _readFileReal(const char *filename, NameSet *rowNames=0, NameSet *colNames=0, DIdxSet *intVars=0)
reads real LP in LP or MPS format from file and returns true on success; gets row names...
Definition: soplex.cpp:8148
decide according to problem size
Definition: soplex.h:1251
UnitVectorBase< Rational > UnitVectorRational
Definition: unitvector.h:31
bool getRedCost(VectorBase< R > &vector) const
gets the vector of reduced cost values if available; returns true on success
Definition: solbase.h:102
Timer * simplexTime
simplex time
Definition: statistics.h:91
void addColsRational(const LPColSetRational &lpcolset)
adds multiple columns
Definition: soplex.cpp:2063
int luSolvesReal
number of (forward and backward) solves with basis matrix in real precision
Definition: statistics.h:107
Real upperReal(int i) const
returns upper bound of column i
Definition: soplex.cpp:972
void getColRational(int i, LPColRational &lpcol) const
gets column i
Definition: soplex.cpp:1206
int refinements
number of refinement steps
Definition: statistics.h:110
const char * getStarterName()
name of starter
Definition: soplex.cpp:5068
void clear()
remove all elements.
Definition: dataarray.h:205
variable fixed to identical bounds.
Definition: spxsolver.h:193
int luFactorizationsReal
number of basis matrix factorizations in real precision
Definition: statistics.h:106
objective sense
Definition: soplex.h:938
bool hasError() const
Definition: mpsinput.h:162
Real getFastCondition(int type=0)
Definition: spxbasis.cpp:1123
int getFactorCount() const
number of factorizations performed
Definition: slufactor.h:248
#define DEFAULT_EPS_UPDATE
Definition: spxdefines.h:236
virtual void removeCol(int i)
Removes i &#39;th column.
Definition: spxlpbase.h:1001
LP has been proven to be primal infeasible.
Definition: spxsolver.h:222
R & value(int n)
Reference to value of n &#39;th nonzero.
Definition: svectorbase.h:252
void setComputeDegenFlag(bool computeDegen)
sets whether the degeneracy is computed at each iteration
Definition: spxsolver.h:2205
Real defaultValue[SoPlex::REALPARAM_COUNT]
array of default values for real parameters
Definition: soplex.h:1396
void _checkBasisScaling()
check correctness of (un)scaled basis matrix operations
Definition: testsoplex.cpp:89
bool readFile(const char *filename, NameSet *rowNames=0, NameSet *colNames=0, DIdxSet *intVars=0)
reads LP file in LP or MPS format according to READMODE parameter; gets row names, column names, and integer variables if desired; returns true on success
Definition: soplex.cpp:5118
void setSparsePricingFactor(Real fac)
Definition: spxsolver.h:847
display frequency
Definition: soplex.h:962
int intParam(const IntParam param) const
returns integer parameter value
Definition: soplex.cpp:5538
void setOpttol(Real d)
set parameter opttol.
Definition: spxsolver.cpp:941
void _ensureRationalLP()
ensures that the rational LP is available; performs no sync
Definition: soplex.cpp:8003
minimum number of stalling refinements since last pivot to trigger rational factorization ...
Definition: soplex.h:1001
minimal reduction (sum of removed rows/cols) to continue simplification
Definition: soplex.h:1328
void getRowVectorReal(int i, DSVectorReal &row) const
gets vector of row i
Definition: soplex.cpp:865
Wrapper for GMP type mpq_class.We wrap mpq_class so that we can replace it by a double type if GMP is...
Definition: rational.h:45
static void setScientific(std::ostream &stream, int precision=8)
Sets the precision of the stream to 16 and the floatfield to scientifix.
Definition: spxout.h:171
geometric mean scaling (max 8 rounds) followed by equilibrium scaling (rows and columns) ...
Definition: soplex.h:1125
bool setSettings(const Settings &newSettings, const bool init=true)
sets parameter settings; returns true on success
Definition: soplex.cpp:6170
void _changeRhsReal(const VectorReal &rhs)
changes right-hand side vector to rhs and adjusts basis
Definition: soplex.cpp:7523
void changeElementReal(int i, int j, const Real &val)
changes matrix entry in row i and column j to val
Definition: soplex.cpp:1681
disable timing
Definition: soplex.h:1235
void printStatistics(std::ostream &os)
prints complete statistics
Definition: soplex.cpp:6767
std::string name[SoPlex::REALPARAM_COUNT]
array of names for real parameters
Definition: soplex.h:1392
Real rhsReal(int i) const
returns right-hand side of row i
Definition: soplex.cpp:900
std::ostream & getStream(const Verbosity &verbosity) const
Returns the stream for the specified verbosity level.
Definition: spxout.h:157
should a rational factorization be performed after iterative refinement?
Definition: soplex.h:894
const SPxPricer * pricer() const
return loaded SPxPricer.
Definition: spxsolver.h:1746
#define REAL_FORMAT
Definition: spxdefines.h:222
virtual bool readBasisFile(const char *filename, const NameSet *rowNames, const NameSet *colNames)
Definition: spxfileio.cpp:24
rowwise representation.
Definition: spxsolver.h:107
mode for hyper sparse pricing
Definition: soplex.h:998
void getRhsReal(DVectorReal &rhs) const
gets right-hand side vector
Definition: soplex.cpp:891
void add(const LPRowBase< R > &row)
Definition: lprowsetbase.h:321
bool setDualNorms(int nnormsRow, int nnormsCol, Real *norms)
set dual norms
Definition: spxsolver.cpp:2020
maximum number of updates without fresh factorization
Definition: soplex.h:950
int dlcmSizeDual(const int base=2) const
returns size of least common multiple of denominators in dual solution
Definition: solbase.h:167
void removeColRangeRational(int start, int end, int perm[]=0)
removes columns start to end including both; an array perm of size numColsRational() may be passed as...
Definition: soplex.cpp:2748
virtual void setTerminationTime(Real time=infinity)
set time limit.
Definition: spxsolver.cpp:1556
void changeUpperRational(const VectorRational &upper)
changes vector of upper bounds to upper
Definition: soplex.cpp:2365
bool _boolParamValues[SoPlex::BOOLPARAM_COUNT]
array of current boolean parameter values
Definition: soplex.h:1421
Rational _rationalPosInfty
Definition: soplex.h:1557
number of integer parameters
Definition: soplex.h:1025
Rational _rationalOpttol
Definition: soplex.h:1560
bool getPrimal(VectorBase< R > &vector) const
gets the primal solution vector; returns true on success
Definition: solbase.h:57
RealParam
real parameters
Definition: soplex.h:1271
virtual void changeObjOffset(const R &o)
Definition: spxlpbase.h:1747
bool setDualNorms(int nnormsRow, int nnormsCol, Real *norms)
sets steepest edge norms and returns false if that&#39;s not possible
Definition: soplex.cpp:1072
static struct soplex::SoPlex::Settings::BoolParam boolParam
Definition: soplex.cpp:551
const VectorRational & lhsRational() const
returns left-hand side vector
Definition: soplex.cpp:1179
virtual void removeRows(int perm[])
Removes multiple rows.
Definition: spxlpbase.h:923
bool writeFileRational(const char *filename, const NameSet *rowNames=0, const NameSet *colNames=0, const DIdxSet *intvars=0) const
writes rational LP to file; LP or MPS format is chosen from the extension in filename; if rowNames an...
Definition: soplex.cpp:5162
void removeLast(int m=1)
remove m last elements.
Definition: dataarray.h:199
maximize number of basic slack variables, i.e. more variables on bounds
Definition: spxsolver.h:230
SPxEquiliSC _scalerBiequi
Definition: soplex.h:1573
int numNonzerosRational() const
returns number of nonzeros
Definition: soplex.cpp:1107
steepest edge pricer with exact initialization of norms
Definition: soplex.h:1163
void getObjUnscaled(VectorBase< Real > &pobj) const
Gets unscaled objective vector.
virtual const std::string what() const
returns exception message
Definition: exceptions.h:57
bool isDualFeasible() const
is stored dual solution feasible?
Definition: soplex.cpp:2928
void removeColRangeReal(int start, int end, int perm[]=0)
removes columns start to end including both; an array perm of size numColsReal() may be passed as buf...
Definition: soplex.cpp:1862
void addColReal(const LPCol &lpcol)
adds a single column
Definition: soplex.cpp:1353
int nRows() const
Returns number of rows in LP.
Definition: spxlpbase.h:151
Rational objRational(int i) const
returns objective value of column i
Definition: soplex.cpp:1288
void add(const SVectorBase< S > &vec)
Append nonzeros of sv.
Definition: dsvectorbase.h:216
void clearLPRational()
clears the LP
Definition: soplex.cpp:2766
No ratiotester loaded.
Definition: spxsolver.h:205
R lower() const
Gets lower bound.
Definition: lpcolbase.h:137
No pricer loaded.
Definition: spxsolver.h:206
void addRowsRational(const LPRowSetRational &lprowset)
adds multiple rows
Definition: soplex.cpp:1977
void printOriginalProblemStatistics(std::ostream &os)
stores the problem statistics of the original problem
Definition: solvedbds.cpp:3536
SPxSolver::Status optimize()
optimize the given LP
Definition: soplex.cpp:2801
void getObjReal(VectorReal &obj) const
gets objective function vector
Definition: soplex.cpp:1018
void getLowerReal(DVectorReal &lower) const
gets lower bound vector
Definition: soplex.cpp:1008
virtual void start()=0
start timer, resume accounting user, system and real time.
Entering Simplex.
Definition: spxsolver.h:134
#define HYPERPRICINGTHRESHOLD
Definition: spxsolver.h:37
void addRowRational(const LPRowRational &lprow)
adds a single row
Definition: soplex.cpp:1912
void addColRational(const LPColRational &lpcol)
adds a single column
Definition: soplex.cpp:1996
virtual Real stop()=0
stop timer, return accounted user time.
int dualDegeneratePivots()
get number of dual degenerate pivots
Definition: spxsolver.h:2067
void spx_alloc(T &p, int n=1)
Allocate memory.
Definition: spxalloc.h:48
std::ostream & getCurrentStream() const
Returns the stream for the current verbosity.
Definition: spxout.h:164
Real getExactCondition()
Definition: spxbasis.h:613
SPxGeometSC _scalerGeoequi
Definition: soplex.h:1576
const UnitVectorRational * _unitVectorRational(const int i)
returns pointer to a constant unit vector available until destruction of the SoPlex class ...
Definition: soplex.cpp:8342
void _rangeToPerm(int start, int end, int *perm, int permSize) const
creates a permutation for removing rows/columns from a range of indices
Definition: soplex.cpp:7202
bool readLine()
reads an MPS format data line and parse the fields.
Definition: mpsinput.cpp:57
void _syncRealSolution()
synchronizes rational solution with real solution, i.e., copies (rounded) rational solution to real s...
Definition: soplex.cpp:8318
Generic Ids for LP rows or columns.Both SPxColIds and SPxRowIds may be treated uniformly as SPxIds: ...
Definition: spxid.h:85
void removeColsRational(int perm[])
removes all columns with an index i such that perm[i] < 0; upon completion, perm[i] >= 0 indicates th...
Definition: soplex.cpp:2699
LP is primal infeasible or unbounded.
Definition: spxsolver.h:223
R objUnscaled(int i) const
Returns unscaled objective value of column i.
refactor threshold for fill-in in current factor update compared to fill-in in last factorization ...
Definition: soplex.h:1334
int nNzos() const
Returns number of nonzeros in LP.
Definition: spxlpbase.h:163
void changeRhsRational(const VectorRational &rhs)
changes right-hand side vector to rhs
Definition: soplex.cpp:2162
virtual void setOutstream(SPxOut &newOutstream)
set message handler
Definition: spxscaler.h:138
Leaving Simplex.
Definition: spxsolver.h:143
standard floating-point parsing
Definition: soplex.h:1199
int dmaxSizeDualRational(const int base=2)
get size of largest denominator in dual solution
Definition: soplex.cpp:3834
void _ensureDSVectorRationalMemory(DSVectorRational &vec, const int newmax) const
extends sparse vector to hold newmax entries if and only if it holds no more free entries ...
Definition: soplex.cpp:7171
Real luFactorizationTimeReal
time for factorizing bases matrices in real precision
Definition: statistics.h:97
void getLowerUnscaled(DVector &vec) const
Gets unscaled lower bound vector.
Real spxLdexp(Real x, int exp)
returns x * 2^exp
Definition: spxdefines.h:352
int dlcmSizePrimalRational(const int base=2)
get size of least common multiple of denominators in primal solution
Definition: soplex.cpp:3792
Rational objValueRational()
returns the objective value if a primal solution is available
Definition: soplex.cpp:3252
void getBasis(SPxSolver::VarStatus rows[], SPxSolver::VarStatus cols[]) const
gets current basis via arrays of statuses
Definition: soplex.cpp:3938
void setNonzeroFactor(Real f)
set refactor threshold for nonzeros in last factorized basis matrix compared to updated basis matrix ...
Definition: spxsolver.h:448
DataArray< SPxSolver::VarStatus > _basisStatusCols
Definition: soplex.h:1816
nothing known about basis status (possibly due to a singular basis in transformed problem) ...
Definition: spxsolver.h:196
decide depending on tolerances whether to apply iterative refinement
Definition: soplex.h:1212
virtual void writeFile(const char *filename, const NameSet *rowNames=0, const NameSet *colNames=0, const DIdxSet *p_intvars=0) const
Write loaded LP to filename.
Definition: spxlpbase.h:1175
void getLhsReal(DVectorReal &lhs) const
gets left-hand side vector
Definition: soplex.cpp:918
SPxStatus status() const
returns current SPxStatus.
Definition: spxbasis.h:425
Real upper[SoPlex::REALPARAM_COUNT]
array of upper bounds for real parameter values
Definition: soplex.h:1400
decompStatus _currentProb
Definition: soplex.h:1804
declaration of types for file output
bool isPrimalFeasible() const
is stored primal solution feasible?
Definition: soplex.cpp:2904
DataArray< RangeType > _colTypes
Definition: soplex.h:1663
type of scaler
Definition: soplex.h:971
automatic choice according to number of rows and columns
Definition: soplex.h:1042
void maxObjUnscaled(VectorBase< Real > &vec) const
Returns unscaled objective vector for maximization problem.
double Real
Definition: spxdefines.h:218
Rational _rationalPosone
Definition: soplex.h:1834
void removeRowRangeReal(int start, int end, int perm[]=0)
removes rows start to end including both; an array perm of size numRowsReal() may be passed as buffer...
Definition: soplex.cpp:1770
SPxBoundFlippingRT _ratiotesterBoundFlipping
Definition: soplex.h:1590
bool _isRealLPLoaded
Definition: soplex.h:1598
SLUFactorRational _rationalLUSolver
Definition: soplex.h:1617
geometric mean scaling on rows and columns, max 8 rounds
Definition: soplex.h:1119
bool isColBasic(int i) const
is the i &#39;th column vector basic ?
Definition: spxsolver.h:1277
void getRowRational(int i, LPRowRational &lprow) const
gets row i
Definition: soplex.cpp:1134
void _solveRealLPAndRecordStatistics()
call floating-point solver and update statistics on iterations etc.
Definition: soplex.cpp:8043
DVectorBase< R > _primal
Definition: solbase.h:218
number of boolean parameters
Definition: soplex.h:931
SPxEquiliSC _scalerUniequi
Definition: soplex.h:1572
#define MSG_DEBUG(x)
Definition: spxdefines.h:132
Status status() const
Status of solution process.
Definition: spxsolve.cpp:1910
Real sumPrimalDegeneracy()
get the sum of primal degeneracy
Definition: spxsolver.h:2085
void printSolvingStatistics(std::ostream &os)
prints statistics on solving process
Definition: soplex.cpp:6745
bool _readFileRational(const char *filename, NameSet *rowNames=0, NameSet *colNames=0, DIdxSet *intVars=0)
reads rational LP in LP or MPS format from file and returns true on success; gets row names...
Definition: soplex.cpp:8189
lower threshold in lifting (nonzero matrix coefficients with smaller absolute value will be reformula...
Definition: soplex.h:1313
bool getPrimalRayReal(VectorReal &vector)
gets the primal ray if available; returns true on success
Definition: soplex.cpp:3003
void getColVectorUnscaled(int i, DSVectorBase< Real > &vec) const
Gets column vector of column i.
bool hasPrimal() const
is a primal feasible solution available?
Definition: soplex.cpp:2912
bool GT(Real a, Real b, Real eps=Param::epsilon())
returns true iff a > b + eps
Definition: spxdefines.h:404
static void setFixed(std::ostream &stream, int precision=8)
Sets the precision of the stream to 8 and the floatfield to fixed.
Definition: spxout.h:177
SPxSense spxSense() const
Returns the optimization sense.
Definition: spxlpbase.h:510
static void setEpsilonPivot(Real eps)
Definition: spxdefines.cpp:80
void changeLhsReal(const VectorReal &lhs)
changes left-hand side vector for constraints to lhs
Definition: soplex.cpp:1408
DVectorBase< Real > DVectorReal
Definition: dvector.h:29
greedy crash basis weighted by objective, bounds, and sides
Definition: soplex.h:1135
bool hasDualFarkas() const
is Farkas proof of infeasibility available?
Definition: soplex.cpp:2944
virtual const char * getName() const
get name of simplifier.
std::string description[SoPlex::INTPARAM_COUNT]
array of descriptions for integer parameters
Definition: soplex.h:1379
bool _isConsistent() const
checks consistency
Definition: soplex.cpp:7214
void _changeLowerReal(const VectorReal &lower)
changes vector of lower bounds to lower and adjusts basis
Definition: soplex.cpp:7641
R upperUnscaled(int i) const
Returns unscaled upper bound of column i.
R lhs() const
Left-hand side value.
Definition: lprowbase.h:203
the iteration frequency at which the decomposition solve output is displayed.
Definition: soplex.h:1016
dual simplex algorithm, i.e., leaving for column and entering for row representation ...
Definition: soplex.h:1058
steepest edge pricer with initialization to unit norms
Definition: soplex.h:1160
LP has been solved to optimality.
Definition: spxsolver.h:220
Rational maxAbsNonzeroRational() const
returns biggest non-zero element in absolute value
Definition: soplex.cpp:1125
use persistent scaling?
Definition: soplex.h:925
VectorBase< Real > Vector
Definition: vector.h:29
virtual void setPricer(SPxPricer *pricer, const bool destroy=false)
setup pricer to use. If destroy is true, pricer will be freed in destructor.
Definition: spxsolver.cpp:103
bool computeBasisInverseRational()
compute rational basis inverse; returns true on success
Definition: soplex.cpp:4878
bool _upperFinite(const RangeType &rangeType) const
checks whether RangeType corresponds to finite upper bound
Definition: soplex.cpp:7326
bool _hasBasis
Definition: soplex.h:1822
use bound flipping also for row representation?
Definition: soplex.h:922
bool hasBasis() const
is an advanced starting basis available?
Definition: soplex.cpp:3848
void _invalidateSolution()
invalidates solution
Definition: soplex.cpp:7925
bool getBasisInverseColReal(int c, Real *coef, int *inds=NULL, int *ninds=NULL, bool unscale=true)
computes column c of basis inverse; returns true on success
Definition: soplex.cpp:4290
bool getDualViolationReal(Real &maxviol, Real &sumviol)
gets violation of dual multipliers; returns true on success
Definition: soplex.cpp:3198
bool getBasisInverseColRational(const int c, SSVectorRational &vec)
computes column c of basis inverse; performs rational factorization if not available; returns true on...
Definition: soplex.cpp:4946
Real sumPrimalDegen
the sum of the rate of primal degeneracy at each iteration
Definition: statistics.h:128
void append(const T &t)
append element t.
Definition: dataarray.h:121
const char * getSimplifierName()
name of simplifier
Definition: soplex.cpp:5079
void changeLowerReal(const VectorReal &lower)
changes vector of lower bounds to lower
Definition: soplex.cpp:1538
DVectorBase< Rational > DVectorRational
Definition: dvector.h:30
virtual void addRows(const LPRowSetBase< R > &pset, bool scale=false)
Definition: spxlpbase.h:635
const char * getPricerName()
name of currently loaded pricer
Definition: soplex.cpp:5101
Class for collecting statistical information.
bool isSPxColId() const
is id a column id?
Definition: spxid.h:165
print condition number during the solve
Definition: soplex.h:1022
void setDisplayFreq(int freq)
set display frequency
Definition: spxsolver.h:829
solve() aborted due to time limit.
Definition: spxsolver.h:212
Rational _rationalNegone
Definition: soplex.h:1835
an error occured.
Definition: spxsolver.h:204
round scaling factors for iterative refinement to powers of two?
Definition: soplex.h:916
const T * get_const_ptr() const
get a const C pointer to the data.
Definition: dataarray.h:115
maximize number of basic slack variables, i.e. more variables on bounds
Definition: soplex.h:1264
SPxBasis::SPxStatus basisStatus() const
returns the current basis status
Definition: soplex.cpp:3856
virtual void setMinReduction(const Real minRed)
set minimal reduction threshold to continue simplification
void removeRowReal(int i)
removes row i
Definition: soplex.cpp:1696
Forrest-Tomlin type update.
Definition: soplex.h:1068
#define DEFAULT_EPS_ZERO
default allowed additive zero: 1.0 + EPS_ZERO == 1.0
Definition: spxdefines.h:230
bool getBasisInverseTimesVecReal(Real *rhs, Real *sol, bool unscale=true)
computes dense solution of basis matrix B * sol = rhs; returns true on success
Definition: soplex.cpp:4495
int dlcmSizeDualRational(const int base=2)
get size of least common multiple of denominators in dual solution
Definition: soplex.cpp:3806
virtual void changeLower(const VectorBase< R > &newLower, bool scale=false)
Changes vector of lower bounds to newLower. scale determines whether the new data should be scaled...
Definition: spxlpbase.h:1346
virtual void setVerbosity(const Verbosity &v)
Definition: spxout.h:111
LPRowBase< R >::Type rowType(int i) const
Returns the inequality type of the i&#39;th LPRow.
Definition: spxlpbase.h:324
SPxWeightST _starterWeight
Definition: soplex.h:1578
Statistics * _statistics
statistics since last call to solveReal() or solveRational()
Definition: soplex.h:1544
#define DEFAULT_EPS_PIVOT
Definition: spxdefines.h:239
virtual void changeRhs(const VectorBase< R > &newRhs, bool scale=false)
Changes right hand side vector for constraints to newRhs. scale determines whether the new data shoul...
Definition: spxlpbase.h:1481
type of simplifier
Definition: soplex.h:968
bool isPrimalFeasible() const
is the stored solution primal feasible?
Definition: solbase.h:51
R obj(int i) const
Returns objective value of column i.
Definition: spxlpbase.h:403
void getColVectorReal(int i, DSVectorReal &col) const
gets vector of col i
Definition: soplex.cpp:954
void solveRight(VectorRational &x, const VectorRational &b)
Solves .
const VectorBase< R > & lhs() const
Returns left hand side vector.
Definition: spxlpbase.h:253
void _removeRowsReal(int perm[])
removes all rows with an index i such that perm[i] < 0; upon completion, perm[i] >= 0 indicates the n...
Definition: soplex.cpp:7826
void _syncLPRational(bool time=true)
synchronizes rational LP with real LP, i.e., copies real LP to rational LP, without looking at the sy...
Definition: soplex.cpp:8299
void printUserSettings()
print non-default parameter values
Definition: soplex.cpp:6217
void changeBoundsReal(const VectorReal &lower, const VectorReal &upper)
changes vectors of column bounds to lower and upper
Definition: soplex.cpp:1613
const char * field3() const
Definition: mpsinput.h:150
RangeType _rangeTypeRational(const Rational &lower, const Rational &upper) const
determines RangeType from rational bounds
Definition: soplex.cpp:7280
SPxSteepPR _pricerQuickSteep
Definition: soplex.h:1585
virtual int getColScaleExp(int i) const
returns scaling factor for column i
Definition: spxscaler.cpp:287
Real getEstimatedCondition()
Definition: spxbasis.h:607
int numColsRational() const
returns number of columns
Definition: soplex.cpp:1098
void syncLPReal()
synchronizes real LP with rational LP, i.e., copies (rounded) rational LP into real LP...
Definition: soplex.cpp:1901
SPxDantzigPR _pricerDantzig
Definition: soplex.h:1582
SPxParMultPR _pricerParMult
Definition: soplex.h:1583
bool getPrimalRational(VectorRational &vector)
gets the primal solution vector if available; returns true on success
Definition: soplex.cpp:3283
void changeObjRational(const VectorRational &obj)
changes objective function vector to obj
Definition: soplex.cpp:2485
std::string statisticString() const
statistical information in form of a string
Definition: soplex.cpp:5052
RangeType _switchRangeType(const RangeType &rangeType) const
switches RANGETYPE_LOWER to RANGETYPE_UPPER and vice versa
Definition: soplex.cpp:7305
SLUFactor _slufactor
Definition: soplex.h:1570
variable set to its upper bound.
Definition: spxsolver.h:191
int primalDegeneratePivots()
get number of primal degenerate pivots
Definition: spxsolver.h:2073
Dynamic index set.Class DIdxSet provides dynamic IdxSet in the sense, that no restrictions are posed ...
Definition: didxset.h:42
void clearBasis()
clears starting basis
Definition: soplex.cpp:5025
const SVectorReal & rowVectorRealInternal(int i) const
returns vector of row i, ignoring scaling
Definition: soplex.cpp:856
void syncLPRational()
synchronizes rational LP with real LP, i.e., copies real LP to rational LP, if sync mode is manual ...
Definition: soplex.cpp:2790
virtual void setRealParam(Real param, const char *name="realparam")
set real parameter
Definition: spxscaler.cpp:118
bool getRedCostReal(VectorReal &vector)
gets the vector of reduced cost values if available; returns true on success
Definition: soplex.cpp:3033
virtual void changeBounds(const VectorBase< R > &newLower, const VectorBase< R > &newUpper, bool scale=false)
Changes variable bounds to newLower and newUpper. scale determines whether the new data should be sca...
Definition: spxlpbase.h:1418
void add(const char *str)
Definition: nameset.cpp:25
int polishIterations()
return number of iterations done with primal algorithm
Definition: spxsolver.h:2110
void getCol(int i, LPColBase< R > &col) const
Gets i &#39;th column.
Definition: spxlpbase.h:336
Real realParam(const RealParam param) const
returns real parameter value
Definition: soplex.cpp:5548
virtual Real time() const =0
~Statistics()
destructor
Definition: statistics.h:52
user sync of real and rational LP
Definition: soplex.h:1192
SPxSteepExPR _pricerSteep
Definition: soplex.h:1586
int boundFlips() const
get number of bound flips.
Definition: spxsolver.h:2061
const char * field0() const
Definition: mpsinput.h:144
int degenPivotsDual
number of dual degenerate pivots
Definition: statistics.h:124
bool hasDual() const
is a dual feasible solution available?
Definition: soplex.cpp:2936
void useFullPerturbation(bool full)
perturb entire problem or only the bounds relevant to the current pivot
Definition: spxsolver.h:876
bool parseSettingsString(char *line)
parses one setting string and returns true on success; note that string is modified ...
Definition: soplex.cpp:6410
const VectorReal & upperRealInternal() const
returns upper bound vector
Definition: soplex.cpp:963
SPxLPBase< Rational > SPxLPRational
Definition: spxlp.h:37
SPxOut spxout
Definition: soplex.h:1444
infinity threshold
Definition: soplex.h:1292
void changeBoundsRational(const VectorRational &lower, const VectorRational &upper)
changes vectors of column bounds to lower and upper
Definition: soplex.cpp:2425
const SVectorRational & colVectorRational(int i) const
returns vector of column i
Definition: soplex.cpp:1224
R lhsUnscaled(int i) const
Returns unscaled left hand side of row number i.
int index(int n) const
Returns index of the n &#39;th nonzero element.
Definition: ssvectorbase.h:174
int numIterations() const
number of iterations since last call to solve
Definition: soplex.cpp:5036
SPxDefaultRT _ratiotesterTextbook
Definition: soplex.h:1587
bool getPrimalRay(VectorBase< R > &vector) const
gets the primal unbounded ray if available; returns true on success
Definition: solbase.h:79
(In)equality for LPs.Class LPRowBase provides constraints for linear programs in the form where a is...
Definition: lprowbase.h:45
int dmaxSizeDual(const int base=2) const
returns size of largest denominator in dual solution
Definition: solbase.h:195
virtual void loadLP(const SPxLP &LP, bool initSlackBasis=true)
copy LP.
Definition: spxsolver.cpp:68
void setSection(Section p_section)
Definition: mpsinput.h:171
variable set to its lower bound.
Definition: spxsolver.h:192
Settings * _currentSettings
Definition: soplex.h:1555
bool getBasisInverseTimesVecRational(const SVectorRational &rhs, SSVectorRational &sol)
computes solution of basis matrix B * sol = rhs; performs rational factorization if not available; re...
Definition: soplex.cpp:4971
SPxId & baseId(int i)
Definition: spxbasis.h:503
virtual const char * getName() const
get name of ratio tester.
Real lhsReal(int i) const
returns left-hand side of row i
Definition: soplex.cpp:927
LPRowReal::Type rowTypeReal(int i) const
returns inequality type of row i
Definition: soplex.cpp:936
Preconfigured SoPlex LP solver.
#define MSG_INFO3(spxout, x)
Prints out message x if the verbosity level is at least SPxOut::INFO3.
Definition: spxdefines.h:122
Sparse vector .A UnitVectorBase is an SVectorBase that can take only one nonzero value with value 1 b...
void _syncRationalSolution()
synchronizes real solution with rational solution, i.e., copies real solution to rational solution ...
Definition: soplex.cpp:8330
int _intParamValues[SoPlex::INTPARAM_COUNT]
array of current integer parameter values
Definition: soplex.h:1424
virtual void changeRow(int n, const LPRowBase< R > &newRow, bool scale=false)
Replaces i &#39;th row of LP with newRow. scale determines whether the new data should be scaled...
Definition: spxlpbase.h:1567
virtual void changeUpper(const VectorBase< R > &newUpper, bool scale=false)
Changes vector of upper bounds to newUpper. scale determines whether the new data should be scaled...
Definition: spxlpbase.h:1382
void reDim(int newdim)
Resets dimension to newdim.
Definition: ssvectorbase.h:566
virtual const char * getName() const
get name of scaler
Definition: spxscaler.cpp:100
bool areLPsInSync(const bool checkVecVals=true, const bool checkMatVals=false, const bool quiet=false) const
checks if real LP and rational LP are in sync; dimensions will always be compared, vector and matrix values only if the respective parameter is set to true. If quiet is set to true the function will only display which vectors are different.
Definition: soplex.cpp:6896
Set of strings.Class NameSet implements a symbol or name table. It allows to store or remove names (i...
Definition: nameset.h:61
partial multiple pricer based on Dantzig pricing
Definition: soplex.h:1154
lower and upper bound finite, but different
Definition: soplex.h:1657
bool isDualFeasible() const
is a dual solution available?
Definition: solbase.h:88
Sequential object-oriented SimPlex.SPxSolver is an LP solver class using the revised Simplex algorith...
Definition: spxsolver.h:84
virtual bool writeBasisFile(const char *filename, const NameSet *rowNames, const NameSet *colNames, const bool cpxFormat=false) const
Definition: spxfileio.cpp:39
equilibrium scaling on rows and columns
Definition: soplex.h:1113
Real luSolveTimeReal
time for solving linear systems in real precision
Definition: statistics.h:98
virtual void changeObj(const VectorBase< R > &newObj, bool scale=false)
Changes objective vector to newObj. scale determines whether the new data should be scaled...
Definition: spxlpbase.h:1278
R * get_ptr()
Only used in slufactor.cpp.
Definition: ssvectorbase.h:99
minimize number of basic slack variables, i.e. more variables between bounds
Definition: soplex.h:1267
Rational _rationalNegInfty
Definition: soplex.h:1558
const SVectorRational & rowVectorRational(int i) const
returns vector of row i
Definition: soplex.cpp:1152
int dlcmSizePrimal(const int base=2) const
returns size of least common multiple of denominators in primal solution
Definition: solbase.h:153
void printStatus(std::ostream &os, SPxSolver::Status status)
prints status
Definition: soplex.cpp:6790
virtual void setTerminationIter(int iteration=-1)
set iteration limit.
Definition: spxsolver.cpp:1568
threshold on number of rows vs. number of columns for switching from column to row representations in...
Definition: soplex.h:1322
lower bound equals upper bound
Definition: soplex.h:1660
virtual void addCol(const LPColBase< R > &col, bool scale=false)
Definition: spxlpbase.h:741
std::string description[SoPlex::REALPARAM_COUNT]
array of descriptions for real parameters
Definition: soplex.h:1394
column representation Ax - s = 0, lower <= x <= upper, lhs <= s <= rhs
Definition: soplex.h:1045
bool getSlacksReal(VectorReal &vector)
gets the vector of slack values if available; returns true on success
Definition: soplex.cpp:2988
#define DEFAULT_RANDOM_SEED
Definition: soplex.h:64
int dim() const
Dimension of vector.
Definition: vectorbase.h:215
automatic pricer
Definition: soplex.h:1148
Exception base class.This class implements a base class for our SoPlex exceptions We provide a what()...
Definition: exceptions.h:32
int size() const
Returns the number of nonzeros.
Definition: ssvectorbase.h:199
Everything should be within this namespace.
bool setRealParam(const RealParam param, const Real value, const bool init=true)
sets real parameter value; returns true on success
Definition: soplex.cpp:5986
void _changeLhsReal(const VectorReal &lhs)
changes left-hand side vector for constraints to lhs and adjusts basis
Definition: soplex.cpp:7482
working tolerance for feasibility in floating-point solver during iterative refinement ...
Definition: soplex.h:1304
SPxLPReal * _realLP
Definition: soplex.h:1592
int max() const
Maximal number of indices.
Definition: svectorbase.h:159
bool _lowerFinite(const RangeType &rangeType) const
checks whether RangeType corresponds to finite lower bound
Definition: soplex.cpp:7318
returns the current git hash of SoPlex
void getCols(int start, int end, LPColSetBase< R > &set) const
Gets columns start, ..., end.
Definition: spxlpbase.h:351
the maximum number of rows that are added in each iteration of the decomposition based simplex ...
Definition: soplex.h:1013
bool loadSettingsFile(const char *filename)
reads settings file; returns true on success
Definition: soplex.cpp:6361
SPxGeometSC _scalerGeo1
Definition: soplex.h:1574
virtual void changeRange(const VectorBase< R > &newLhs, const VectorBase< R > &newRhs, bool scale=false)
Changes left and right hand side vectors. scale determines whether the new data should be scaled...
Definition: spxlpbase.h:1505
int numNonzerosReal() const
returns number of nonzeros
Definition: soplex.cpp:815
SoPlex & operator=(const SoPlex &rhs)
assignment operator
Definition: soplex.cpp:621
bool getRedCostViolationRational(Rational &maxviol, Rational &sumviol)
gets violation of reduced costs; returns true on success
Definition: soplex.cpp:3477
SPxDevexPR _pricerDevex
Definition: soplex.h:1584
void clear()
Remove all indices.
Definition: svectorbase.h:422
virtual void setTester(SPxRatioTester *tester, const bool destroy=false)
setup ratio-tester to use. If destroy is true, tester will be freed in destructor.
Definition: spxsolver.cpp:130
Real objReal(int i) const
returns objective value of column i
Definition: soplex.cpp:1027
DataArray< RangeType > _rowTypes
Definition: soplex.h:1664
void _removeColReal(int i)
removes column i
Definition: soplex.cpp:7861
void _changeRowReal(int i, const LPRowReal &lprow)
replaces row i with lprow and adjusts basis
Definition: soplex.cpp:7457
void setIntegralityInformation(int ncols, int *intInfo)
pass integrality information about the variables to the solver
Definition: soplex.cpp:1080
SPxSumST _starterSum
Definition: soplex.h:1579
bool readStringRational(const char *s, Rational &value)
read Rational from string
Definition: rational.cpp:3462
void getBasisInd(int *bind) const
gets the indices of the basic columns and rows; basic column n gives value n, basic row m gives value...
Definition: soplex.cpp:3978
row representation (lower,lhs) <= (x,Ax) <= (upper,rhs)
Definition: soplex.h:1048
apply rational reconstruction after each iterative refinement?
Definition: soplex.h:913
void _changeColReal(int i, const LPColReal &lpcol)
replaces column i with lpcol and adjusts basis
Definition: soplex.cpp:7614
solve() aborted due to detection of cycling.
Definition: spxsolver.h:211
Real minAbsNonzeroReal() const
returns smallest non-zero element in absolute value
Definition: soplex.cpp:824
type of pricer
Definition: soplex.h:977
Saving LPs in a form suitable for SoPlex.Class SPxLPBase provides the data structures required for sa...
Definition: spxlpbase.h:80
const VectorReal & lowerRealInternal() const
returns lower bound vector
Definition: soplex.cpp:990
bool getDualReal(VectorReal &vector)
gets the dual solution vector if available; returns true on success
Definition: soplex.cpp:3018
SPxHarrisRT _ratiotesterHarris
Definition: soplex.h:1588
DSVectorBase< Real > DSVectorReal
Definition: dsvector.h:29
void changeColReal(int i, const LPColReal &lpcol)
replaces column i with lpcol
Definition: soplex.cpp:1519
working tolerance for optimality in floating-point solver during iterative refinement ...
Definition: soplex.h:1307
void clearLPReal()
clears the LP
Definition: soplex.cpp:1880
Preconfigured SoPlex LP-solver.
Definition: soplex.h:90
should the dual of the complementary problem be used in the decomposition simplex?
Definition: soplex.h:904
void removeRowRational(int i)
removes row i
Definition: soplex.cpp:2577
R lowerUnscaled(int i) const
Returns unscaled lower bound of column i.
#define MSG_WARNING(spxout, x)
Prints out message x if the verbosity level is at least SPxOut::WARNING.
Definition: spxdefines.h:116
Type
(In)Equality type of an LP row.
Definition: lprowbase.h:72
int iterations
number of iterations/pivots
Definition: statistics.h:101
const VectorBase< R > & maxObj() const
Returns objective vector for maximization problem.
Definition: spxlpbase.h:429
virtual const char * getName() const
get name of pricer.
Definition: spxpricer.h:104
R upper() const
Gets upper bound.
Definition: lpcolbase.h:125
int upper[SoPlex::INTPARAM_COUNT]
array of upper bounds for int parameter values
Definition: soplex.h:1385
Real lower[SoPlex::REALPARAM_COUNT]
array of lower bounds for real parameter values
Definition: soplex.h:1398
SPxVectorST _starterVector
Definition: soplex.h:1580
void setIntegralityInformation(int ncols, int *intInfo)
pass integrality information about the variables to the solver
Definition: spxsolver.cpp:2049
void setup()
Initializes nonzero indices for elements with absolute values above epsilon and sets all other elemen...
Definition: ssvectorbase.h:132
#define SET_MAX_LINE_LEN
maximum length of lines in settings file
Definition: soplex.cpp:36
static void setEpsilonUpdate(Real eps)
Definition: spxdefines.cpp:70
bool getBoundViolationReal(Real &maxviol, Real &sumviol)
gets violation of bounds; returns true on success
Definition: soplex.cpp:3063
bool writeFileReal(const char *filename, const NameSet *rowNames=0, const NameSet *colNames=0, const DIdxSet *intvars=0, const bool unscale=true) const
writes real LP to file; LP or MPS format is chosen from the extension in filename; if rowNames and co...
Definition: soplex.cpp:5136
const VectorRational & upperRational() const
returns upper bound vector
Definition: soplex.cpp:1233
void setConditionInformation(int condInfo)
print condition number within the usual output
Definition: spxsolver.h:841
NameSet * _colNames
Definition: soplex.h:1778
int boundflips
number of dual bound flips
Definition: statistics.h:105
decide according to READMODE
Definition: soplex.h:1225
void clearAllData()
clears all statistics
Definition: statistics.cpp:90
SPxSolver _solver
Definition: soplex.h:1569
const char * getGitHash()
Definition: spxgithash.cpp:23
mode for a posteriori feasibility checks
Definition: soplex.h:992
refactor threshold for nonzeros in last factorized basis matrix compared to updated basis matrix ...
Definition: soplex.h:1331
nothing known on loaded problem.
Definition: spxsolver.h:219
don&#39;t perform modifications on optimal basis
Definition: spxsolver.h:229
VarStatus getBasisRowStatus(int row) const
gets basis status for a single row
Definition: spxsolver.cpp:1788
int _optimizeCalls
Definition: soplex.h:1831
variable is basic.
Definition: spxsolver.h:195
LPRowRational::Type rowTypeRational(int i) const
returns inequality type of row i
Definition: soplex.cpp:1197
type of algorithm, i.e., primal or dual
Definition: soplex.h:944
const SVectorBase< R > & rowVector(int i) const
Gets row vector of row i.
Definition: spxlpbase.h:204
VarStatus getBasisColStatus(int col) const
gets basis status for a single column
Definition: spxsolver.cpp:1794
void print(std::ostream &os)
prints statistics
Definition: statistics.cpp:149
void clearSolvingData()
clears statistics on solving process
Definition: statistics.cpp:97
void _recomputeRangeTypesReal()
recomputes range types from scratch using real LP
Definition: soplex.cpp:8249
virtual void addRow(const LPRowBase< R > &row, bool scale=false)
Definition: spxlpbase.h:580
std::string name[SoPlex::INTPARAM_COUNT]
array of names for integer parameters
Definition: soplex.h:1377
#define DEFAULT_REFACTOR_INTERVAL
default setting for LU refactorization interval
Definition: soplex.cpp:38
DataArray< UnitVectorRational *> _unitMatrixRational
Definition: soplex.h:1639
bool getDualFarkasRational(VectorRational &vector)
gets the Farkas proof if LP is infeasible; returns true on success
Definition: soplex.cpp:3358
stalling refinement limit (-1 if unlimited)
Definition: soplex.h:959
int lower[SoPlex::INTPARAM_COUNT]
array of lower bounds for int parameter values
Definition: soplex.h:1383
DataArray< SPxSolver::VarStatus > _basisStatusRows
Definition: soplex.h:1815
std::ifstream spxifstream
Definition: spxfileio.h:43
Set of LP rows.Class LPRowSetBase implements a set of LPRowBase%s. Unless for memory limitations...
Definition: lprowsetbase.h:44
Timer * readingTime
reading time not included in solving time
Definition: statistics.h:88
int iterationsFromBasis
number of iterations from Basis
Definition: statistics.h:103
int iterationsPolish
number of iterations during solution polishing
Definition: statistics.h:104
SPxSolver::VarStatus basisColStatus(int col) const
returns basis status for a single column
Definition: soplex.cpp:3902
void _solveDecompositionDualSimplex()
solves LP using the decomposition based dual simplex
Definition: solvedbds.cpp:48
void getNdualNorms(int &nnormsRow, int &nnormsCol) const
gets number of available dual norms
Definition: soplex.cpp:1056
should dual infeasibility be tested in order to try to return a dual solution even if primal infeasib...
Definition: soplex.h:891
int defaultValue[SoPlex::INTPARAM_COUNT]
array of default values for integer parameters
Definition: soplex.h:1381
virtual void changeSense(SPxSense sns)
Changes optimization sense to sns.
Definition: spxlpbase.h:1737
bool getFastCondition(Real &condition, int type=0)
compute condition number estimate based on the diagonal of the LU factorization; returns true on succ...
Definition: soplex.cpp:4059
void getUpperUnscaled(DVector &vec) const
Gets unscaled upper bound vector.
uint32_t getSeed() const
returns the initial seed shift
Definition: random.h:113
Timer * solvingTime
solving time
Definition: statistics.h:89
int size() const
return nr. of elements.
Definition: dataarray.h:211
generic solution-based crash basis
Definition: soplex.h:1141
std::string description[SoPlex::BOOLPARAM_COUNT]
array of descriptions for boolean parameters
Definition: soplex.h:1368
Type type() const
return current Type.
Definition: spxsolver.h:484
const VectorReal & rhsRealInternal() const
returns right-hand side vector, ignoring scaling
Definition: soplex.cpp:882
bool boolParam(const BoolParam param) const
returns boolean parameter value
Definition: soplex.cpp:5528
void setSeed(uint32_t initshift)
initialize all seeds of the random number generator.
Definition: random.h:124
void unscaleLP()
unscales the lp and clears basis
virtual const char * getName() const
get name of starter.
Definition: spxstarter.h:88
the verbosity of the decomposition based simplex
Definition: soplex.h:1019
const VectorBase< R > & upper() const
Definition: lpcolsetbase.h:166
Real getSolveTime() const
time spent in solves
Definition: slufactor.h:253
should lifting be used to reduce range of nonzero matrix coefficients?
Definition: soplex.h:885
void printProblemStatistics(std::ostream &os)
Definition: spxlpbase.h:1192
int dmaxSizePrimalRational(const int base=2)
get size of largest denominator in primal solution
Definition: soplex.cpp:3820
bool getEstimatedCondition(Real &condition)
computes an estimated condition number for the current basis matrix using the power method; returns t...
Definition: soplex.cpp:4074
int dmaxSizePrimal(const int base=2) const
returns size of largest denominator in primal solution
Definition: solbase.h:181
Real maxObjReal(int i) const
returns objective value of column i after transformation to a maximization problem; since this is how...
Definition: soplex.cpp:1047
void setRandomSeed(unsigned int seed)
set the random seeds of the solver instance
Definition: soplex.cpp:7155
DataArray< int > _rationalLUSolverBind
Definition: soplex.h:1618
should the degeneracy be computed for each basis?
Definition: soplex.h:901
#define MSG_INFO1(spxout, x)
Prints out message x if the verbosity level is at least SPxOut::INFO1.
Definition: spxdefines.h:118
bool _applyPolishing
Definition: soplex.h:1601
bool getExactCondition(Real &condition)
computes the exact condition number for the current basis matrix using the power method; returns true...
Definition: soplex.cpp:4089
SPxStatus
basis status.
Definition: spxbasis.h:90
virtual int getRowScaleExp(int i) const
returns scaling factor for row i
Definition: spxscaler.cpp:294
const char * getScalerName()
name of scaling method
Definition: soplex.cpp:5090
Real solveTime() const
time spent in last call to solve
Definition: soplex.cpp:5044
void addColsReal(const LPColSetReal &lpcolset)
adds multiple columns
Definition: soplex.cpp:1371
const SVectorBase< R > & colVector(int i) const
Returns column vector of column i.
Definition: spxlpbase.h:373
Random random
The random number generator used throughout the whole computation. Its seed can be modified...
Definition: spxsolver.h:399
const char * field1() const
Definition: mpsinput.h:146
int nCols() const
Returns number of columns in LP.
Definition: spxlpbase.h:157
virtual void changeElement(int i, int j, const R &val, bool scale=false)
Changes LP element (i, j) to val. scale determines whether the new data should be scaled...
Definition: spxlpbase.h:1657
SPxSolver::Status status() const
returns the current solver status
Definition: soplex.cpp:2896
SolReal _solReal
Definition: soplex.h:1818
zero tolerance used in update of the factorization
Definition: soplex.h:1286
int iterationsPrimal
number of iterations with Primal
Definition: statistics.h:102
void changeLowerRational(const VectorRational &lower)
changes vector of lower bounds to lower
Definition: soplex.cpp:2305
lower limit on objective value
Definition: soplex.h:1298
both bounds are infinite
Definition: soplex.h:1648
bool getRedCostViolationReal(Real &maxviol, Real &sumviol)
gets violation of reduced costs; returns true on success
Definition: soplex.cpp:3144
BoolParam
boolean parameters
Definition: soplex.h:882
bool _hasSolReal
Definition: soplex.h:1823
bool _isSolveStopped(bool &stoppedTime, bool &stoppedIter) const
should solving process be stopped?
Definition: soplex.cpp:7240
virtual void changeLhs(const VectorBase< R > &newLhs, bool scale=false)
Changes left hand side vector for constraints to newLhs. scale determines whether the new data should...
Definition: spxlpbase.h:1449
virtual Real getCoefUnscaled(const SPxLPBase< Real > &lp, int row, int col) const
returns unscaled coefficient of lp
Definition: spxscaler.cpp:594
void _changeBoundsReal(const VectorReal &lower, const VectorReal &upper)
changes vectors of column bounds to lower and upper and adjusts basis
Definition: soplex.cpp:7725
#define SOPLEX_SUBVERSION
Definition: spxdefines.h:46
Settings()
default constructor initializing default settings
Definition: soplex.cpp:510
maximum number of conjugate gradient iterations in least square scaling
Definition: soplex.h:1004
sparse pricing threshold (#violations < dimension * SPARSITY_THRESHOLD activates sparse pricing) ...
Definition: soplex.h:1319
Settings & operator=(const Settings &settings)
assignment operator
Definition: soplex.cpp:532
void setFeastol(Real d)
set parameter feastol.
Definition: spxsolver.cpp:929
bool getDualFarkas(VectorBase< R > &vector) const
gets the Farkas proof if available; returns true on success
Definition: solbase.h:116
void addRowReal(const LPRowReal &lprow)
adds a single row
Definition: soplex.cpp:1317
static void setEpsilonFactorization(Real eps)
Definition: spxdefines.cpp:60
bool getPrimalRayRational(VectorRational &vector)
gets the primal ray if LP is unbounded; returns true on success
Definition: soplex.cpp:3313
dual feasibility tolerance
Definition: soplex.h:1277
void _ensureRealLPLoaded()
ensures that the real LP and the basis are loaded in the solver; performs no sync ...
Definition: soplex.cpp:8016
void invalidate()
invalidate solution
Definition: solbase.h:209
no solution polishing
Definition: soplex.h:1261
void changeRowReal(int i, const LPRowReal &lprow)
replaces row i with lprow
Definition: soplex.cpp:1389
void setBasis(const SPxSolver::VarStatus rows[], const SPxSolver::VarStatus cols[])
sets starting basis via arrays of statuses
Definition: soplex.cpp:4995
bool hasPrimalRay() const
is a primal unbounded ray available?
Definition: solbase.h:73
bool setIntParam(const IntParam param, const int value, const bool init=true)
sets integer parameter value; returns true on success
Definition: soplex.cpp:5632
void solve(Vector &x, const Vector &rhs)
Definition: spxbasis.h:631
SolRational _solRational
Definition: soplex.h:1819
void getLhsUnscaled(VectorBase< Real > &vec) const
Returns unscaled left hand side vector.
bool saveSettingsFile(const char *filename, const bool onlyChanged=false) const
writes settings file; returns true on success
Definition: soplex.cpp:6276
UnitVectorBase< Real > UnitVectorReal
Definition: unitvector.h:30
std::string rationalToString(const Rational &r, const int precision)
convert rational number to string
Definition: rational.cpp:3452
Real objValueReal()
returns the objective value if a primal solution is available
Definition: soplex.cpp:2952
bool _parseSettingsLine(char *line, const int lineNumber)
parses one line in a settings file and returns true on success; note that the string is modified ...
Definition: soplex.cpp:8365
void changeRhsReal(const VectorReal &rhs)
changes right-hand side vector to rhs
Definition: soplex.cpp:1445
SPxLeastSqSC _scalerLeastsq
Definition: soplex.h:1577
geometric frequency at which to apply rational reconstruction
Definition: soplex.h:1325
Real opttol() const
allowed optimality, i.e., dual feasibility tolerance.
Definition: spxsolver.h:794
void changeElementRational(int i, int j, const Rational &val)
changes matrix entry in row i and column j to val
Definition: soplex.cpp:2541
bool isRowBasic(int i) const
is the i &#39;th row vector basic ?
Definition: spxsolver.h:1271
SPxStarter * _starter
Definition: soplex.h:1596
bool _hasSolRational
Definition: soplex.h:1824
void hyperPricing(bool h)
enable or disable hyper sparse pricing
Definition: spxsolver.cpp:963
void writeStateRational(const char *filename, const NameSet *rowNames=0, const NameSet *colNames=0, const bool cpxFormat=false) const
writes internal LP, basis information, and parameter settings; if rowNames and colNames are NULL...
Definition: soplex.cpp:5508
void _enableSimplifierAndScaler()
enables simplifier and scaler according to current parameters
Definition: soplex.cpp:7940
primal simplex algorithm, i.e., entering for column and leaving for row representation ...
Definition: soplex.h:1055
bool setBoolParam(const BoolParam param, const bool value, const bool init=true)
sets boolean parameter value; returns true on success
Definition: soplex.cpp:5578
should LP be transformed to equality form before a rational solve?
Definition: soplex.h:888
void setOutstream(SPxOut &newOutstream)
Definition: spxsolver.h:441
const char * field2() const
Definition: mpsinput.h:148
Real sumDualDegen
the sum of the rate of dual degeneracy at each iteration
Definition: statistics.h:127
void _idxToPerm(int *idx, int idxSize, int *perm, int permSize) const
creates a permutation for removing rows/columns from an array of indices
Definition: soplex.cpp:7181
DVectorBase< R > _dual
Definition: solbase.h:221
virtual void clear()
clears the LP.
Definition: spxlpbase.h:1098
void setMemFactor(Real f)
set refactor threshold for memory growth in current factor update compared to the last factorization ...
Definition: spxsolver.h:460
void solveLeft(VectorRational &x, const VectorRational &b)
Solves .
int number(const DataKey &pkey) const
returns number of name with DataKey pkey in NameSet.
Definition: nameset.h:212
const SPxBasis & basis() const
Return current basis.
Definition: spxsolver.h:1736
SPxSolver::VarStatus basisRowStatus(int row) const
returns basis status for a single row
Definition: soplex.cpp:3877
the number of iterations before the decomposition simplex initialisation is terminated.
Definition: soplex.h:1010
store only real LP
Definition: soplex.h:1186
virtual void reLoad()
reload LP.
Definition: spxsolver.cpp:55
const VectorRational & maxObjRational() const
returns objective function vector after transformation to a maximization problem; since this is how i...
Definition: soplex.cpp:1298
upper threshold in lifting (nonzero matrix coefficients with larger absolute value will be reformulat...
Definition: soplex.h:1316
void _addRowsReal(const LPRowSetReal &lprowset)
adds multiple rows to the real LP and adjusts basis
Definition: soplex.cpp:7370
int numColsReal() const
returns number of columns
Definition: soplex.cpp:806
virtual Status solve()
solve loaded LP.
Definition: spxsolve.cpp:73
LP has been proven to be primal unbounded.
Definition: spxbasis.h:98
void changeUpperReal(const VectorReal &upper)
changes vector of upper bounds to upper
Definition: soplex.cpp:1576
void reSize(int newsize)
reset size to newsize.
Definition: dataarray.h:223
bool hasPrimalRay() const
is a primal unbounded ray available?
Definition: soplex.cpp:2920
void removeColRational(int i)
removes column i
Definition: soplex.cpp:2672
bool _isRealLPScaled
Definition: soplex.h:1600
IntParam
integer parameters
Definition: soplex.h:935
force iterative refinement
Definition: soplex.h:1215
const VectorBase< R > & lower() const
Returns (internal and possibly scaled) lower bound vector.
Definition: spxlpbase.h:483
~NameSet()
destructor.
Definition: nameset.cpp:259
SPxSolver::Status _status
Definition: soplex.h:1812
void setTiming(Timer::TYPE ttype)
set timing type
Definition: spxsolver.h:816
virtual R maxAbsNzo(bool unscaled=true) const
Absolute biggest non-zero element in (in rational case possibly scaled) LP.
void getObjRational(VectorRational &obj) const
gets objective function vector
Definition: soplex.cpp:1269
int num() const
Returns the number of LPColBases currently in LPColSetBase.
Definition: lpcolsetbase.h:82
virtual void setIntParam(int param, const char *name="intparam")
set int parameter
Definition: spxscaler.cpp:121
virtual void computePrimalActivity(const VectorBase< R > &primal, VectorBase< R > &activity, const bool unscaled=true) const
Computes activity of the rows for a given primal vector; activity does not need to be zero...
Rational _rationalZero
Definition: soplex.h:1836
LP column.Class LPColBase provides a datatype for storing the column of an LP a the form similar to ...
Definition: lpcolbase.h:45
Representation rep() const
return the current basis representation.
Definition: spxsolver.h:478
RangeType _rangeTypeReal(const Real &lower, const Real &upper) const
determines RangeType from real bounds
Definition: soplex.cpp:7255
void _completeRangeTypesRational()
completes range type arrays after adding columns and/or rows
Definition: soplex.cpp:8236
const VectorReal & lhsRealInternal() const
returns left-hand side vector, ignoring scaling
Definition: soplex.cpp:909
solve() aborted due to objective limit.
Definition: spxsolver.h:214
columnwise representation.
Definition: spxsolver.h:108
void spx_free(T &p)
Release memory.
Definition: spxalloc.h:109
SPxSimplifier * _simplifier
Definition: soplex.h:1594
void removeRowRangeRational(int start, int end, int perm[]=0)
removes rows start to end including both; an array perm of size numRowsRational() may be passed as bu...
Definition: soplex.cpp:2654
void addRowsReal(const LPRowSetReal &lprowset)
adds multiple rows
Definition: soplex.cpp:1335
bool has(int pnum) const
does NameSet has a name with number pnum?
Definition: nameset.h:231
geometric mean scaling on rows and columns, max 1 round
Definition: soplex.h:1116
virtual void addCols(const LPColSetBase< R > &pset, bool scale=false)
Definition: spxlpbase.h:793
void scaleValue(int i, int scaleExp)
Scale i &#39;th element by a.
Definition: ssvectorbase.h:242
perturb the entire problem or only the relevant bounds of s single pivot?
Definition: soplex.h:928
Basis is singular, numerical troubles?
Definition: spxsolver.h:215
R value(int n) const
Returns value of the n &#39;th nonzero element.
Definition: ssvectorbase.h:182
const SVector & unitVector(int i) const
return i &#39;th unit vector.
Definition: spxsolver.h:1217
should row and bound violations be computed explicitly in the update of reduced problem in the decomp...
Definition: soplex.h:907
Basis is primal feasible.
Definition: spxbasis.h:96
upper bound is finite, lower bound is infinite
Definition: soplex.h:1654
bool getBoundViolationRational(Rational &maxviol, Rational &sumviol)
gets violation of bounds; returns true on success
Definition: soplex.cpp:3373
LP has a usable Basis (maybe LP is changed).
Definition: spxsolver.h:217
SPxAutoPR _pricerAuto
Definition: soplex.h:1581
int num() const
Returns the number of LPRowBases in LPRowSetBase.
Definition: lprowsetbase.h:83
int primalIterations()
return number of iterations done with primal algorithm
Definition: spxsolver.h:2097
least square scaling
Definition: soplex.h:1122
only error output
Definition: soplex.h:1075
void setMax(int newmax=1)
Reset nonzero memory to >= newmax.
Definition: dsvectorbase.h:248
LP has been proven to be primal unbounded.
Definition: spxsolver.h:221
int totalSizeDualRational(const int base=2)
get size of dual solution
Definition: soplex.cpp:3778
int degenPivotsPrimal
number of primal degenerate pivots
Definition: statistics.h:123
LP has been proven to be primal infeasible.
Definition: spxbasis.h:99
No Problem has been loaded to the basis.
Definition: spxbasis.h:92
No linear solver loaded.
Definition: spxsolver.h:207
void removeRowsReal(int perm[])
removes all rows with an index i such that perm[i] < 0; upon completion, perm[i] >= 0 indicates the n...
Definition: soplex.cpp:1722
const VectorRational & lowerRational() const
returns lower bound vector
Definition: soplex.cpp:1251
#define SPX_MAXSTRLEN
Definition: spxdefines.h:249