Changeset 2411
 Timestamp:
 Mar 6, 2019 7:13:19 PM (8 months ago)
 Location:
 branches/ghpages
 Files:

 2 added
 1 edited
Legend:
 Unmodified
 Added
 Removed

branches/ghpages/basicmodelclasses.md
r2410 r2411 1 Basic Model Classes {#basicmodelclasses}1 Basic Model Classes 2 2 =================== 3 3 … … 23 23 user only need call `model.dual()` to invoke the dual simplex method. 24 24 25 First Example {#firstexample}25 First Example 26 26 ============= 27 27 28 28 Below is our first CLP sample program. It is short enough to present in 29 29 full (this code can be found in the CLP Samples directory, see 30 [ ???](#moreexamples)). Most of the remaining examples in this Guide will30 [here](./moresamples)). Most of the remaining examples in this Guide will 31 31 take the form of small code fragments. 32 32 33 34 // Copyright (C) 2002, International Business Machines 35 // Corporation and others. All Rights Reserved. 36 37 #include "ClpSimplex.hpp" 38 int main (int argc, const char *argv[]) 39 { 40 ClpSimplex model; 41 int status; 42 if (argc<2) 43 status=model.readMps("../../Mps/Sample/p0033.mps"); 44 else 45 status=model.readMps(argv[1]); 46 if (!status) { 47 model.primal(); 48 } 49 return 0; 50 } 51 52 33 ``` 34 // Copyright (C) 2002, International Business Machines 35 // Corporation and others. All Rights Reserved. 36 37 #include "ClpSimplex.hpp" 38 int main (int argc, const char *argv[]) 39 { 40 ClpSimplex model; 41 int status; 42 if (argc<2) 43 status=model.readMps("../../Mps/Sample/p0033.mps"); 44 else 45 status=model.readMps(argv[1]); 46 if (!status) { 47 model.primal(); 48 } 49 return 0; 50 } 51 ``` 53 52 54 53 This sample program creates a `ClpSimplex` model, reads an MPS file, and … … 56 55 program is easy to follow, but it is not terribly useful: it does not 57 56 attempt to inspect the results of the solve. There are two main kinds of 58 results: a \"status\" describing what happened to the model during the57 results: a "status" describing what happened to the model during the 59 58 solve, and arrays filled with solution values. Both will be addressed in 60 59 this chapter. 61 60 62 Getting at the Solution {#gettingsolution}61 Getting at the Solution 63 62 ======================= 64 63 65 64 It is often the case with CLP that there is more than one way to do 66 something. This is a consequence of CLP \'s mixed heritage as a child of65 something. This is a consequence of CLP's mixed heritage as a child of 67 66 [OSL](http://www306.ibm.com/software/data/bi/osl/) and a cousin of 68 [OSI](http://www. coinor.org/faqs.html#OSI). Finding the status of a67 [OSI](http://www.github.com/coinor/OSI). Finding the status of a 69 68 model exemplifies this situation. 70 69 71 The OSI way to check for optimality is to call model.isProvenOptimal().70 The OSI way to check for optimality is to call `model.isProvenOptimal()`. 72 71 Also available are `isProvenPrimalInfeasible()`, 73 72 `isProvenDualInfeasible()`, `isPrimalObjectiveLimitReached()`, … … 79 78 Similarly, to pick up the solution values, one could inhabit the 80 79 virtuous world of OSI, or the notquitesovirtuous world of OSL and 81 \"pure\" CLP. By this it is meant that const and nonconst forms of80 "pure" CLP. By this it is meant that const and nonconst forms of 82 81 arrays are used, respectively. It is easier to deal with the nonconst 83 82 versions, so most of the elaborate algorithms in CLP and its 84 [Samples]( #moresamples) use them.85 86 Purpose OSIstyle (virtuous) CLPstyle (less virtuous) 87    88 Primal column solution `const double * getColSolution()` `double * primalColumnSolution()` 89 Dual row solution `const double * getRowPrice()` `double * dualColumnSolution()` 90 Primal row solution `const double * getRowActivity()` `double * primalRowSolution()` 91 Dual row solution `const double * getReducedCost()` `double * dualColumnSolution()` 92 Number of rows in model `int getNumRows()` `int numberRows()` 93 Number of columns in model `int getNumCols()` `int numberColumns()` 94 95 : Methods for getting solution information 96 97 The reader may have noted a preference for \"number\" over \"num\" and98 \"column\" over \"col\". This may be a reaction to when one of the83 [Samples](./moresamples) use them. 84 85 Methods for getting solution information: 86 87 Purpose  OSIstyle (virtuous)  CLPstyle (less virtuous)  88  89 Primal column solution  `const double * getColSolution()`  `double * primalColumnSolution()`  90 Dual row solution  `const double * getRowPrice()`  `double * dualColumnSolution()`  91 Primal row solution  `const double * getRowActivity()`  `double * primalRowSolution()`  92 Dual row solution  `const double * getReducedCost()`  `double * dualColumnSolution()`  93 Number of rows in model  `int getNumRows()`  `int numberRows()`  94 Number of columns in model  `int getNumCols()`  `int numberColumns()`  95 96 The reader may have noted a preference for "number" over "num" and 97 "column" over "col". This may be a reaction to when one of the 99 98 authors was young and 5 or 6 letters was the maximum in FORTRAN for any 100 99 name or to early days with OSL when seven characters were allowed but 101 the first three had to be \"ekk\"!102 103 Using the abovelisted functions, our [initial example](#firstexample)100 the first three had to be "ekk"! 101 102 Using the abovelisted functions, our initial example 104 103 might be continued as follows: 105 106 107 int numberRows = model.numberRows(); 108 double * rowPrimal = model.primalRowSolution(); 109 double * rowDual = model.dualRowSolution(); 110 111 int iRow; 112 113 for (iRow=0;iRow<numberRows;iRow++) 114 printf("Row %d, primal %g, dual %g\n",iRow, 115 rowPrimal[iRow],rowDual[iRow]); 116 117 int numberColumns = model.numberColumns(); 118 double * columnPrimal = model.primalColumnSolution(); 119 double * columnDual = model.dualColumnSolution(); 120 121 int iColumn; 122 123 for (iColumn=0;iColumn<numberColumns;iColumn++) 124 printf("Column %d, primal %g, dual %g\n",iColumn, 125 columnPrimal[iColumn],columnDual[iColumn]); 126 127 128 129 This code sample would prettyprint information about the model\'s 104 ``` 105 int numberRows = model.numberRows(); 106 double * rowPrimal = model.primalRowSolution(); 107 double * rowDual = model.dualRowSolution(); 108 109 int iRow; 110 111 for (iRow=0;iRow<numberRows;iRow++) 112 printf("Row %d, primal %g, dual %g\n",iRow,rowPrimal[iRow],rowDual[iRow]); 113 114 int numberColumns = model.numberColumns(); 115 double * columnPrimal = model.primalColumnSolution(); 116 double * columnDual = model.dualColumnSolution(); 117 118 int iColumn; 119 120 for (iColumn=0;iColumn<numberColumns;iColumn++) 121 printf("Column %d, primal %g, dual %g\n",iColumn, 122 columnPrimal[iColumn],columnDual[iColumn]); 123 ``` 124 125 This code sample would prettyprint information about the model's 130 126 primal and dual solutions. How to additionally print row and column 131 names is illustrated in the `defaults.cpp` file in the \"Samples\"132 directory (the Samples are properly addressed in [???](#moreexamples)).127 names is illustrated in the `defaults.cpp` file in the "Samples" 128 directory (the Samples are properly addressed [here](./moresamples)). 133 129 This sample is also useful as it explicitly performs default actions 134 130 (e.g. it sets the primal feasiblility tolerance value to the default … … 138 134 user might wish to perform. Apart from presolve we will only be looking 139 135 at actions which can be performed when including the single header file 140 `C OIN/Clp/include/ClpSimplex.hpp`.141 142 Building and Modifying a Model {#buildandmodify}136 `ClpSimplex.hpp`. 137 138 Building and Modifying a Model 143 139 ============================== 144 140 … … 154 150 size of a model. The simplest is by the use of the method 155 151 `resize(newNumberRows,newNumberColumns)`  this will either truncate the 156 model or add \"default\" rows or columns  a default row has lower bound152 model or add "default" rows or columns  a default row has lower bound 157 153 of infinity and upper bound of +infinity, while a default column has 158 154 zero cost, zero lower bound and an upper bound of +infinity. … … 186 182 was stated as for minimization; signs are reversed for maximization.) 187 183 188 Some Useful Set and Get Methods {#setsandgets}184 Some Useful Set and Get Methods 189 185 =============================== 190 186 191 Method(s) Description 192   193 `setMaximumIterations(int value)` `int maximumIterations()` `setMaximumSeconds(double value)` `double maximumIterations()` These methods tell CLP to stop after a given number of iterations or seconds (and returns these values). 194 `doubleÂ objectiveValue()` This method returns the objective value. 195 `constÂ doubleÂ *Â getObjCoefficients()` `doubleÂ *Â objective()` These methods return the objective coefficients. 196 `constÂ doubleÂ *Â getRowLower()` `doubleÂ *Â rowLower()` `constÂ doubleÂ *Â getRowUpper()` `doubleÂ *Â rowUpper()` `constÂ doubleÂ *Â getColLower()` `doubleÂ *Â columnLower()` `constÂ doubleÂ *Â getColUpper()` `doubleÂ *Â columnUpper()` These methods give lower and upper bounds on row and column activities. 197 `double * infeasibilityRay()` `double * unboundedRay()` If the problem was primal or dual infeasible, these methods will give a pointer to a ray proving infeasibility. 198 `CoinPackMatrix * matrix()` There are more options as the user has great flexibility in how the problem matrix is stored, but the default matrix class is `CoinPackedMatrix` (see [???](#matrixclasses)). So we have that this method returns a pointer to a `CoinPackedMatrix` which can be further manipulated. 199 `CoinBigIndexÂ getNumElements()` [^1] Returns the number of elements in the problem matrix. 200 `void setOptimizationDirection(doubleÂ value)` `double optimizationDirection()` These methods set and get the objective sense. The parameter `value` should be +1 to minimize, 1 to maximize, and 0 to ignore. 201 202 : Some Useful Set and Get Methods 203 204 Simplexspecific Methods {#simplexspecific} 187  Method(s)  Description  188   189  `setMaximumIterations(int value)` `int maximumIterations()` `setMaximumSeconds(double value)` `double maximumIterations()`  These methods tell CLP to stop after a given number of iterations or seconds (and returns these values).  190  `doubleÂ objectiveValue()`  This method returns the objective value.  191  `constÂ doubleÂ *Â getObjCoefficients()` `doubleÂ *Â objective()`  These methods return the objective coefficients.  192  `constÂ doubleÂ *Â getRowLower()` `doubleÂ *Â rowLower()` `constÂ doubleÂ *Â getRowUpper()` `doubleÂ *Â rowUpper()` `constÂ doubleÂ *Â getColLower()` `doubleÂ *Â columnLower()` `constÂ doubleÂ *Â getColUpper()` `doubleÂ *Â columnUpper()`  These methods give lower and upper bounds on row and column activities.  193  `double * infeasibilityRay()` `double * unboundedRay()`  If the problem was primal or dual infeasible, these methods will give a pointer to a ray proving infeasibility.  194  `CoinPackMatrix * matrix()`  There are more options as the user has great flexibility in how the problem matrix is stored, but the default matrix class is `CoinPackedMatrix` (see Matrix Classes [here](./notsobasic)). So we have that this method returns a pointer to a `CoinPackedMatrix` which can be further manipulated.  195  `CoinBigIndexÂ getNumElements()`  Returns the number of elements in the problem matrix. `CoinBigIndex` is a `typedef` which in most cases is the same as `int`.  196  `void setOptimizationDirection(doubleÂ value)` `double optimizationDirection()`  These methods set and get the objective sense. The parameter `value` should be +1 to minimize, 1 to maximize, and 0 to ignore.  197 198 Simplexspecific Methods 205 199 ======================== 206 200 207 201 Some of the most commonlyused methods when working with Simplex are 208 listed in the table below. 209 210 Method(s) Description 211   212 `primal(intÂ mode=0)` This applies the primal algorithm. If `mode` is set to the default of 0, then the method uses the status variables to determine basis and solution. If `mode` is 1 then the method does a values pass so variables not in basis are given their current values and one pass of variables is done to clean up the basis with an equal or better objective value. 213 `dual(intÂ mode=0)` This applies the dual algorithm. if `mode` is set to the default of 0, then the method uses the status variables to determine basis and solution. If `mode` is 1 then the method uses input duals and does a values pass so one pass of basic variables is done to clean up the duals with an equal or better objective value. 214 `scaling(intÂ mode=1)` This method toggles scaling on (`mode` set to 1) and off (`mode` set to 0). 215 `intÂ crash(doubleÂ gap,intÂ mode)` This method attemps to improve on an all slack basis. For dual this will move variables to the dual feasible bound if the gap between bounds is less than `gap`. Setting `mode` to 0 guesses which algorithm is better, while a value of 1 or 2 will result in more work being done. The return code is 0 if the basis was not slacks in first case, it is negative if dual is preferred or positive if primal. Â±1 means an all slack basis seemed best, while Â±2 means some work was done. 216 `perturb(intÂ mode)` This method toggles perturbation on (`mode` set to 1) and off (`mode` set to 0). It should be considered a work in progress, although on some problems it gives very good results. 217 `factorizationFrequency()` `setFactorizationFrequency(intÂ value)` These are \"get\" and \"set\" methods for the basis matrix factorization frequency. The default is to refactor every 200 iterations, but it may make more sense to use something such as 100 + the number of rows divided by 50. 218 `dualBound()` `setDualBound(doubleÂ value)` These are \"get\" and \"set\" methods for the \"dualÂ bound\". The CLP dual algorithm declares all problems to be dual feasible by putting nonbasic variables to correct bounds for the reduced cost. If the gap between the bounds is too big then it pretends the gap is only the value specified by this set method. In essence, this gives a composite dual rather than a pure PhaseÂ I PhaseÂ II method. 219 `infeasibilityCost()` `setInfeasibilityCost(doubleÂ value)` These are the primal analogs to the \"dualÂ bound\" methods. 220 `numberPrimalInfeasibilities()` `sumPrimalInfeasibilities()` After a solve, there may be infeasibilities. These methods serve to check for said infeasibilities. One could check the solution explicitly as well. For a code fragement illustrating this, see [example\_title](#presolveexample). 221 222 : Common Simplexspecific methods 202 listed in the following table: 203 204  Method(s)  Description 205   206  `primal(intÂ mode=0)`  This applies the primal algorithm. If `mode` is set to the default of 0, then the method uses the status variables to determine basis and solution. If `mode` is 1 then the method does a values pass so variables not in basis are given their current values and one pass of variables is done to clean up the basis with an equal or better objective value. 207  `dual(intÂ mode=0)`  This applies the dual algorithm. if `mode` is set to the default of 0, then the method uses the status variables to determine basis and solution. If `mode` is 1 then the method uses input duals and does a values pass so one pass of basic variables is done to clean up the duals with an equal or better objective value. 208  `scaling(intÂ mode=1)`  This method toggles scaling on (`mode` set to 1) and off (`mode` set to 0). 209  `intÂ crash(doubleÂ gap,intÂ mode)`  This method attemps to improve on an all slack basis. For dual this will move variables to the dual feasible bound if the gap between bounds is less than `gap`. Setting `mode` to 0 guesses which algorithm is better, while a value of 1 or 2 will result in more work being done. The return code is 0 if the basis was not slacks in first case, it is negative if dual is preferred or positive if primal. Â±1 means an all slack basis seemed best, while Â±2 means some work was done. 210  `perturb(intÂ mode)`  This method toggles perturbation on (`mode` set to 1) and off (`mode` set to 0). It should be considered a work in progress, although on some problems it gives very good results. 211  `factorizationFrequency()` `setFactorizationFrequency(intÂ value)`  These are "get" and "set" methods for the basis matrix factorization frequency. The default is to refactor every 200 iterations, but it may make more sense to use something such as 100 + the number of rows divided by 50. 212  `dualBound()` `setDualBound(doubleÂ value)`  These are "get" and "set" methods for the "dualÂ bound". The CLP dual algorithm declares all problems to be dual feasible by putting nonbasic variables to correct bounds for the reduced cost. If the gap between the bounds is too big then it pretends the gap is only the value specified by this set method. In essence, this gives a composite dual rather than a pure PhaseÂ I PhaseÂ II method. 213  `infeasibilityCost()` `setInfeasibilityCost(doubleÂ value)`  These are the primal analogs to the "dualÂ bound" methods. 214  `numberPrimalInfeasibilities()` `sumPrimalInfeasibilities()`  After a solve, there may be infeasibilities. These methods serve to check for said infeasibilities. One could check the solution explicitly as well. For a code fragement illustrating this, see the following example.  223 215 224 216 Presolve 225 217 ======== 226 218 227 The header file for the use of CLP\'s presolve functionality is 228 `COIN/Clp/include/Presolve.hpp`. The sample program below illustrates 229 some of the possibilities offered by CLP\'s presolve: 230 231 #include "ClpSimplex.hpp" 232 #include "ClpPresolve.hpp" 233 int main (int argc, const char *argv[]) 234 { 235 ClpSimplex model; 236 model.readMps("../../Mps/Sample/p0033.mps"); // initialized by readMps or whatever 237 ClpPresolve presolveInfo; 238 ClpSimplex * presolvedModel = presolveInfo.presolvedModel(model); 239 // at this point we have original model and a new model. The information 240 // on the operations done is in presolveInfo 241 if (presolvedModel) { 242 // was not found to be infeasible  so lets solve 243 // if presolvedModel was NULL then it was primal infeasible and ... 244 presolvedModel>dual(); // or whatever else we wish to do 245 presolveInfo.postsolve(true); // the true updates status arrays in original 246 /* If the presolved model was optimal then so should the 247 original be. 248 We can use checkSolution and test feasibility */ 249 model.checkSolution(); 250 if (model.numberDualInfeasibilities() 251 model.numberPrimalInfeasibilities()) 252 printf("%g dual %g(%d) Primal %g(%d)\n", 253 model.objectiveValue(), 254 model.sumDualInfeasibilities(), 255 model.numberDualInfeasibilities(), 256 model.sumPrimalInfeasibilities(), 257 model.numberPrimalInfeasibilities()); 258 // Due to tolerances we can not guarantee that so you may wish to throw in 259 model.primal(1); 260 } 261 } 262 219 The header file for the use of CLP's presolve functionality is 220 `Presolve.hpp`. The sample program below illustrates 221 some of the possibilities offered by CLP's presolve: 222 ``` 223 #include "ClpSimplex.hpp" 224 #include "ClpPresolve.hpp" 225 226 int main (int argc, const char *argv[]) 227 { 228 ClpSimplex model; 229 model.readMps("../../Data/Sample/p0033.mps"); // initialized by readMps or whatever 230 ClpPresolve presolveInfo; 231 ClpSimplex * presolvedModel = presolveInfo.presolvedModel(model); 232 // at this point we have original model and a new model. The information 233 // on the operations done is in presolveInfo 234 if (presolvedModel) { 235 // was not found to be infeasible  so lets solve 236 // if presolvedModel was NULL then it was primal infeasible and ... 237 presolvedModel>dual(); // or whatever else we wish to do 238 presolveInfo.postsolve(true); // the true updates status arrays in original 239 /* If the presolved model was optimal then so should the original be. 240 We can use checkSolution and test feasibility */ 241 model.checkSolution(); 242 if (model.numberDualInfeasibilities() model.numberPrimalInfeasibilities()) 243 printf("%g dual %g(%d) Primal %g(%d)\n", 244 model.objectiveValue(), 245 model.sumDualInfeasibilities(), 246 model.numberDualInfeasibilities(), 247 model.sumPrimalInfeasibilities(), 248 model.numberPrimalInfeasibilities()); 249 // Due to tolerances we can not guarantee that so you may wish to throw in 250 model.primal(1); 251 } 252 } 253 ``` 263 254 264 255 Presolve has a few more options which can be found in the header file, … … 266 257 row and column names. 267 258 268 Status Array {#statusarray}259 Status Array 269 260 ============ 270 261 … … 273 264 Nevertheless, for completeness the status of a variable can be found and 274 265 set as shown below. The possible state of a variable are listed in the 275 following table (each may have to be preceded by ClpSimplex::): 276 277 `Status`[^2] Description 278   279 `basic` In basis 280 `isFree` Not in basis, has infinite bounds 281 `isFixed` Not in basis, bounds are equal 282 `atUpperBound` At upper bound, not in basis 283 `atLowerBound` At lower bound, not in basis 284 `superBasic` Between bounds, but not basic or free 285 286 : Possible states of a variable 266 following table (each may have to be preceded by `ClpSimplex::`): 267 268  Status  Description  269   270  `basic`  In basis  271  `isFree`  Not in basis, has infinite bounds  272  `isFixed`  Not in basis, bounds are equal  273  `atUpperBound`  At upper bound, not in basis  274  `atLowerBound`  At lower bound, not in basis  275  `superBasic`  Between bounds, but not basic or free  287 276 288 277 To get or set the status of a variable is a simple task: 289 290 // Get row status... 291 Status status=model.getRowStatus(sequenceNumber) 292 // ... or get column status. 293 Status status=model.getColumnStatus(sequenceNumber) 294 // Set row status to basic (for example)... 295 model.setRowStatus(sequenceNumber,ClpSimplex::basic) 296 // ... or column status to basic. 297 model.setColumnStatus(sequenceNumber,ClpSimplex::basic) 298 299 300 [^1]: `CoinBigIndex` is a `typedef` which in most cases is the same as 301 `int`. 302 303 [^2]: `Status` is an enumeration. 278 ``` 279 // Get row status... 280 Status status=model.getRowStatus(sequenceNumber) 281 // ... or get column status. 282 Status status=model.getColumnStatus(sequenceNumber) 283 // Set row status to basic (for example)... 284 model.setRowStatus(sequenceNumber,ClpSimplex::basic) 285 // ... or column status to basic. 286 model.setColumnStatus(sequenceNumber,ClpSimplex::basic) 287 ```
Note: See TracChangeset
for help on using the changeset viewer.