1 // $Id$ 2 // Copyright (C) 2000, International Business Machines 3 // Corporation and others. All Rights Reserved. 4 // This code is licensed under the terms of the Eclipse Public License (EPL). 5 6 #ifndef OsiCbcSolverInterface_H 7 #define OsiCbcSolverInterface_H 8 9 #include <string> 10 #include <cfloat> 11 #include <map> 12 #include "CbcModel.hpp" 13 #include "CoinPackedMatrix.hpp" 14 #include "OsiSolverInterface.hpp" 15 #include "CbcStrategy.hpp" 16 #include "CoinWarmStartBasis.hpp" 17 18 class OsiRowCut; 19 class OsiClpSolverInterface; 20 static const double OsiCbcInfinity = COIN_DBL_MAX; 21 22 //############################################################################# 23 24 /** Cbc Solver Interface 25 26 Instantiation of OsiCbcSolverInterface for the Model Algorithm. 27 28 */ 29 30 class OsiCbcSolverInterface : virtual public OsiSolverInterface { 31 friend void OsiCbcSolverInterfaceUnitTest(const std::string &mpsDir, const std::string &netlibDir); 32 33 public: 34 //--------------------------------------------------------------------------- 35 /**@name Solve methods */ 36 //@{ 37 /// Solve initial LP relaxation 38 virtual void initialSolve(); 39 40 /// Resolve an LP relaxation after problem modification 41 virtual void resolve(); 42 43 /// Invoke solver's built-in enumeration algorithm 44 virtual void branchAndBound(); 45 //@} 46 47 //--------------------------------------------------------------------------- 48 /**@name Parameter set/get methods 49 50 The set methods return true if the parameter was set to the given value, 51 false otherwise. There can be various reasons for failure: the given 52 parameter is not applicable for the solver (e.g., refactorization 53 frequency for the cbc algorithm), the parameter is not yet implemented 54 for the solver or simply the value of the parameter is out of the range 55 the solver accepts. If a parameter setting call returns false check the 56 details of your solver. 57 58 The get methods return true if the given parameter is applicable for the 59 solver and is implemented. In this case the value of the parameter is 60 returned in the second argument. Otherwise they return false. 61 */ 62 //@{ 63 // Set an integer parameter 64 bool setIntParam(OsiIntParam key, int value); 65 // Set an double parameter 66 bool setDblParam(OsiDblParam key, double value); 67 // Set a string parameter 68 bool setStrParam(OsiStrParam key, const std::string &value); 69 // Get an integer parameter 70 bool getIntParam(OsiIntParam key, int &value) const; 71 // Get an double parameter 72 bool getDblParam(OsiDblParam key, double &value) const; 73 // Get a string parameter 74 bool getStrParam(OsiStrParam key, std::string &value) const; 75 // Set a hint parameter - overrides OsiSolverInterface 76 virtual bool setHintParam(OsiHintParam key, bool yesNo = true, 77 OsiHintStrength strength = OsiHintTry, 78 void *otherInformation = NULL); 79 /// Get a hint parameter 80 virtual bool getHintParam(OsiHintParam key, bool &yesNo, 81 OsiHintStrength &strength, 82 void *&otherInformation) const; 83 84 using OsiSolverInterface::getHintParam; 85 /// Get a hint parameter 86 virtual bool getHintParam(OsiHintParam key, bool &yesNo, 87 OsiHintStrength &strength) const; 88 //@} 89 90 //--------------------------------------------------------------------------- 91 ///@name Methods returning info on how the solution process terminated 92 //@{ 93 /// Are there a numerical difficulties? 94 virtual bool isAbandoned() const; 95 /// Is optimality proven? 96 virtual bool isProvenOptimal() const; 97 /// Is primal infeasiblity proven? 98 virtual bool isProvenPrimalInfeasible() const; 99 /// Is dual infeasiblity proven? 100 virtual bool isProvenDualInfeasible() const; 101 /// Is the given primal objective limit reached? 102 virtual bool isPrimalObjectiveLimitReached() const; 103 /// Is the given dual objective limit reached? 104 virtual bool isDualObjectiveLimitReached() const; 105 /// Iteration limit reached? 106 virtual bool isIterationLimitReached() const; 107 //@} 108 109 //--------------------------------------------------------------------------- 110 /**@name WarmStart related methods */ 111 //@{ 112 113 /*! \brief Get an empty warm start object 114 115 This routine returns an empty CoinWarmStartBasis object. Its purpose is 116 to provide a way to give a client a warm start basis object of the 117 appropriate type, which can resized and modified as desired. 118 */ 119 120 virtual CoinWarmStart *getEmptyWarmStart() const; 121 122 /// Get warmstarting information 123 virtual CoinWarmStart *getWarmStart() const; 124 /** Set warmstarting information. Return true/false depending on whether 125 the warmstart information was accepted or not. */ 126 virtual bool setWarmStart(const CoinWarmStart *warmstart); 127 //@} 128 129 //--------------------------------------------------------------------------- 130 /**@name Hotstart related methods (primarily used in strong branching). <br> 131 The user can create a hotstart (a snapshot) of the optimization process 132 then reoptimize over and over again always starting from there.<br> 133 <strong>NOTE</strong>: between hotstarted optimizations only 134 bound changes are allowed. */ 135 //@{ 136 /// Create a hotstart point of the optimization process 137 virtual void markHotStart(); 138 /// Optimize starting from the hotstart 139 virtual void solveFromHotStart(); 140 /// Delete the snapshot 141 virtual void unmarkHotStart(); 142 //@} 143 144 //--------------------------------------------------------------------------- 145 /**@name Problem information methods 146 147 These methods call the solver's query routines to return 148 information about the problem referred to by the current object. 149 Querying a problem that has no data associated with it result in 150 zeros for the number of rows and columns, and NULL pointers from 151 the methods that return vectors. 152 153 Const pointers returned from any data-query method are valid as 154 long as the data is unchanged and the solver is not called. 155 */ 156 //@{ 157 /**@name Methods related to querying the input data */ 158 //@{ 159 /// Get number of columns 160 virtual int getNumCols() const; 161 162 /// Get number of rows 163 virtual int getNumRows() const; 164 165 /// Get number of nonzero elements 166 virtual CoinBigIndex getNumElements() const; 167 168 /// Get pointer to array[getNumCols()] of column lower bounds 169 virtual const double *getColLower() const; 170 171 /// Get pointer to array[getNumCols()] of column upper bounds 172 virtual const double *getColUpper() const; 173 174 /** Get pointer to array[getNumRows()] of row constraint senses. 175 <ul> 176 <li>'L' <= constraint 177 <li>'E' = constraint 178 <li>'G' >= constraint 179 <li>'R' ranged constraint 180 <li>'N' free constraint 181 </ul> 182 */ 183 virtual const char *getRowSense() const; 184 185 /** Get pointer to array[getNumRows()] of rows right-hand sides 186 <ul> 187 <li> if rowsense()[i] == 'L' then rhs()[i] == rowupper()[i] 188 <li> if rowsense()[i] == 'G' then rhs()[i] == rowlower()[i] 189 <li> if rowsense()[i] == 'R' then rhs()[i] == rowupper()[i] 190 <li> if rowsense()[i] == 'N' then rhs()[i] == 0.0 191 </ul> 192 */ 193 virtual const double *getRightHandSide() const; 194 195 /** Get pointer to array[getNumRows()] of row ranges. 196 <ul> 197 <li> if rowsense()[i] == 'R' then 198 rowrange()[i] == rowupper()[i] - rowlower()[i] 199 <li> if rowsense()[i] != 'R' then 200 rowrange()[i] is undefined 201 </ul> 202 */ 203 virtual const double *getRowRange() const; 204 205 /// Get pointer to array[getNumRows()] of row lower bounds 206 virtual const double *getRowLower() const; 207 208 /// Get pointer to array[getNumRows()] of row upper bounds 209 virtual const double *getRowUpper() const; 210 211 /// Get pointer to array[getNumCols()] of objective function coefficients 212 virtual const double *getObjCoefficients() const; 213 214 /// Get objective function sense (1 for min (default), -1 for max) 215 virtual double getObjSense() const; 216 217 /// Return true if column is continuous 218 virtual bool isContinuous(int colNumber) const; 219 220 /// Get pointer to row-wise copy of matrix 221 virtual const CoinPackedMatrix *getMatrixByRow() const; 222 223 /// Get pointer to column-wise copy of matrix 224 virtual const CoinPackedMatrix *getMatrixByCol() const; 225 226 /// Get solver's value for infinity 227 virtual double getInfinity() const; 228 //@} 229 230 /**@name Methods related to querying the solution */ 231 //@{ 232 /// Get pointer to array[getNumCols()] of primal solution vector 233 virtual const double *getColSolution() const; 234 235 /// Get pointer to array[getNumRows()] of dual prices 236 virtual const double *getRowPrice() const; 237 238 /// Get a pointer to array[getNumCols()] of reduced costs 239 virtual const double *getReducedCost() const; 240 241 /** Get pointer to array[getNumRows()] of row activity levels (constraint 242 matrix times the solution vector */ 243 virtual const double *getRowActivity() const; 244 245 /// Get objective function value 246 virtual double getObjValue() const; 247 248 /** Get how many iterations it took to solve the problem (whatever 249 "iteration" mean to the solver. */ 250 virtual int getIterationCount() const; 251 252 /** Get as many dual rays as the solver can provide. (In case of proven 253 primal infeasibility there should be at least one.) 254 255 The first getNumRows() ray components will always be associated with 256 the row duals (as returned by getRowPrice()). If \c fullRay is true, 257 the final getNumCols() entries will correspond to the ray components 258 associated with the nonbasic variables. If the full ray is requested 259 and the method cannot provide it, it will throw an exception. 260 261 <strong>NOTE for implementers of solver interfaces:</strong> <br> 262 The double pointers in the vector should point to arrays of length 263 getNumRows() and they should be allocated via new[]. <br> 264 265 <strong>NOTE for users of solver interfaces:</strong> <br> 266 It is the user's responsibility to free the double pointers in the 267 vector using delete[]. 268 */ 269 virtual std::vector< double * > getDualRays(int maxNumRays, 270 bool fullRay = false) const; 271 /** Get as many primal rays as the solver can provide. (In case of proven 272 dual infeasibility there should be at least one.) 273 274 <strong>NOTE for implementers of solver interfaces:</strong> <br> 275 The double pointers in the vector should point to arrays of length 276 getNumCols() and they should be allocated via new[]. <br> 277 278 <strong>NOTE for users of solver interfaces:</strong> <br> 279 It is the user's responsibility to free the double pointers in the 280 vector using delete[]. 281 */ 282 virtual std::vector< double * > getPrimalRays(int maxNumRays) const; 283 284 //@} 285 286 /*! \name Methods for row and column names. 287 288 Because OsiCbc is a pass-through class, it's necessary to override any 289 virtual method in order to be sure we catch an override by the underlying 290 solver. See the OsiSolverInterface class documentation for detailed 291 descriptions. 292 */ 293 //@{ 294 295 /*! \brief Generate a standard name of the form Rnnnnnnn or Cnnnnnnn */ 296 297 virtual std::string dfltRowColName(char rc, 298 int ndx, unsigned digits = 7) const; 299 300 /*! \brief Return the name of the objective function */ 301 302 virtual std::string getObjName(std::string::size_type maxLen = std::string::npos) const; 303 304 /*! \brief Set the name of the objective function */ 305 306 virtual void setObjName(std::string name); 307 308 /*! \brief Return the name of the row. */ 309 310 virtual std::string getRowName(int rowIndex, 311 std::string::size_type maxLen = std::string::npos) const; 312 313 /*! \brief Return a pointer to a vector of row names */ 314 315 virtual const OsiNameVec &getRowNames(); 316 317 /*! \brief Set a row name */ 318 319 virtual void setRowName(int ndx, std::string name); 320 321 /*! \brief Set multiple row names */ 322 323 virtual void setRowNames(OsiNameVec &srcNames, 324 int srcStart, int len, int tgtStart); 325 326 /*! \brief Delete len row names starting at index tgtStart */ 327 328 virtual void deleteRowNames(int tgtStart, int len); 329 330 /*! \brief Return the name of the column */ 331 332 virtual std::string getColName(int colIndex, 333 std::string::size_type maxLen = std::string::npos) const; 334 335 /*! \brief Return a pointer to a vector of column names */ 336 337 virtual const OsiNameVec &getColNames(); 338 339 /*! \brief Set a column name */ 340 341 virtual void setColName(int ndx, std::string name); 342 343 /*! \brief Set multiple column names */ 344 345 virtual void setColNames(OsiNameVec &srcNames, 346 int srcStart, int len, int tgtStart); 347 348 /*! \brief Delete len column names starting at index tgtStart */ 349 virtual void deleteColNames(int tgtStart, int len); 350 351 //@} 352 353 //@} 354 355 //--------------------------------------------------------------------------- 356 357 /**@name Problem modifying methods */ 358 //@{ 359 //------------------------------------------------------------------------- 360 /**@name Changing bounds on variables and constraints */ 361 //@{ 362 /** Set an objective function coefficient */ 363 virtual void setObjCoeff(int elementIndex, double elementValue); 364 365 using OsiSolverInterface::setColLower; 366 /** Set a single column lower bound<br> 367 Use -DBL_MAX for -infinity. */ 368 virtual void setColLower(int elementIndex, double elementValue); 369 370 using OsiSolverInterface::setColUpper; 371 /** Set a single column upper bound<br> 372 Use DBL_MAX for infinity. */ 373 virtual void setColUpper(int elementIndex, double elementValue); 374 375 /** Set a single column lower and upper bound */ 376 virtual void setColBounds(int elementIndex, 377 double lower, double upper); 378 379 /** Set the bounds on a number of columns simultaneously<br> 380 The default implementation just invokes setColLower() and 381 setColUpper() over and over again. 382 @param indexFirst,indexLast pointers to the beginning and after the 383 end of the array of the indices of the variables whose 384 <em>either</em> bound changes 385 @param boundList the new lower/upper bound pairs for the variables 386 */ 387 virtual void setColSetBounds(const int *indexFirst, 388 const int *indexLast, 389 const double *boundList); 390 391 /** Set a single row lower bound<br> 392 Use -DBL_MAX for -infinity. */ 393 virtual void setRowLower(int elementIndex, double elementValue); 394 395 /** Set a single row upper bound<br> 396 Use DBL_MAX for infinity. */ 397 virtual void setRowUpper(int elementIndex, double elementValue); 398 399 /** Set a single row lower and upper bound */ 400 virtual void setRowBounds(int elementIndex, 401 double lower, double upper); 402 403 /** Set the type of a single row<br> */ 404 virtual void setRowType(int index, char sense, double rightHandSide, 405 double range); 406 407 /** Set the bounds on a number of rows simultaneously<br> 408 The default implementation just invokes setRowLower() and 409 setRowUpper() over and over again. 410 @param indexFirst,indexLast pointers to the beginning and after the 411 end of the array of the indices of the constraints whose 412 <em>either</em> bound changes 413 @param boundList the new lower/upper bound pairs for the constraints 414 */ 415 virtual void setRowSetBounds(const int *indexFirst, 416 const int *indexLast, 417 const double *boundList); 418 419 /** Set the type of a number of rows simultaneously<br> 420 The default implementation just invokes setRowType() 421 over and over again. 422 @param indexFirst,indexLast pointers to the beginning and after the 423 end of the array of the indices of the constraints whose 424 <em>any</em> characteristics changes 425 @param senseList the new senses 426 @param rhsList the new right hand sides 427 @param rangeList the new ranges 428 */ 429 virtual void setRowSetTypes(const int *indexFirst, 430 const int *indexLast, 431 const char *senseList, 432 const double *rhsList, 433 const double *rangeList); 434 //@} 435 436 //------------------------------------------------------------------------- 437 /**@name Integrality related changing methods */ 438 //@{ 439 /** Set the index-th variable to be a continuous variable */ 440 virtual void setContinuous(int index); 441 /** Set the index-th variable to be an integer variable */ 442 virtual void setInteger(int index); 443 /** Set the variables listed in indices (which is of length len) to be 444 continuous variables */ 445 virtual void setContinuous(const int *indices, int len); 446 /** Set the variables listed in indices (which is of length len) to be 447 integer variables */ 448 virtual void setInteger(const int *indices, int len); 449 //@} 450 451 //------------------------------------------------------------------------- 452 /// Set objective function sense (1 for min (default), -1 for max,) 453 virtual void setObjSense(double s); 454 455 /** Set the primal solution column values 456 457 colsol[numcols()] is an array of values of the problem column 458 variables. These values are copied to memory owned by the 459 solver object or the solver. They will be returned as the 460 result of colsol() until changed by another call to 461 setColsol() or by a call to any solver routine. Whether the 462 solver makes use of the solution in any way is 463 solver-dependent. 464 */ 465 virtual void setColSolution(const double *colsol); 466 467 /** Set dual solution vector 468 469 rowprice[numrows()] is an array of values of the problem row 470 dual variables. These values are copied to memory owned by the 471 solver object or the solver. They will be returned as the 472 result of rowprice() until changed by another call to 473 setRowprice() or by a call to any solver routine. Whether the 474 solver makes use of the solution in any way is 475 solver-dependent. 476 */ 477 virtual void setRowPrice(const double *rowprice); 478 479 //------------------------------------------------------------------------- 480 /**@name Methods to expand a problem.<br> 481 Note that if a column is added then by default it will correspond to a 482 continuous variable. */ 483 //@{ 484 using OsiSolverInterface::addCol; 485 /** */ 486 virtual void addCol(const CoinPackedVectorBase &vec, 487 const double collb, const double colub, 488 const double obj); 489 /** Add a column (primal variable) to the problem. */ 490 virtual void addCol(int numberElements, const int *rows, const double *elements, 491 const double collb, const double colub, 492 const double obj); 493 494 using OsiSolverInterface::addCols; 495 /** */ 496 virtual void addCols(const int numcols, 497 const CoinPackedVectorBase *const *cols, 498 const double *collb, const double *colub, 499 const double *obj); 500 /** */ 501 virtual void deleteCols(const int num, const int *colIndices); 502 503 using OsiSolverInterface::addRow; 504 /** */ 505 virtual void addRow(const CoinPackedVectorBase &vec, 506 const double rowlb, const double rowub); 507 /** */ 508 virtual void addRow(const CoinPackedVectorBase &vec, 509 const char rowsen, const double rowrhs, 510 const double rowrng); 511 512 using OsiSolverInterface::addRows; 513 /** */ 514 virtual void addRows(const int numrows, 515 const CoinPackedVectorBase *const *rows, 516 const double *rowlb, const double *rowub); 517 /** */ 518 virtual void addRows(const int numrows, 519 const CoinPackedVectorBase *const *rows, 520 const char *rowsen, const double *rowrhs, 521 const double *rowrng); 522 /** */ 523 virtual void deleteRows(const int num, const int *rowIndices); 524 525 //----------------------------------------------------------------------- 526 /** Apply a collection of row cuts which are all effective. 527 applyCuts seems to do one at a time which seems inefficient. 528 */ 529 virtual void applyRowCuts(int numberCuts, const OsiRowCut *cuts); 530 /** Apply a collection of row cuts which are all effective. 531 applyCuts seems to do one at a time which seems inefficient. 532 This uses array of pointers 533 */ 534 virtual void applyRowCuts(int numberCuts, const OsiRowCut **cuts); 535 //@} 536 //@} 537 538 //--------------------------------------------------------------------------- 539 540 public: 541 /**@name Methods to input a problem */ 542 //@{ 543 /** Load in an problem by copying the arguments (the constraints on the 544 rows are given by lower and upper bounds). If a pointer is 0 then the 545 following values are the default: 546 <ul> 547 <li> <code>colub</code>: all columns have upper bound infinity 548 <li> <code>collb</code>: all columns have lower bound 0 549 <li> <code>rowub</code>: all rows have upper bound infinity 550 <li> <code>rowlb</code>: all rows have lower bound -infinity 551 <li> <code>obj</code>: all variables have 0 objective coefficient 552 </ul> 553 */ 554 virtual void loadProblem(const CoinPackedMatrix &matrix, 555 const double *collb, const double *colub, 556 const double *obj, 557 const double *rowlb, const double *rowub); 558 559 /** Load in an problem by assuming ownership of the arguments (the 560 constraints on the rows are given by lower and upper bounds). For 561 default values see the previous method. <br> 562 <strong>WARNING</strong>: The arguments passed to this method will be 563 freed using the C++ <code>delete</code> and <code>delete[]</code> 564 functions. 565 */ 566 virtual void assignProblem(CoinPackedMatrix *&matrix, 567 double *&collb, double *&colub, double *&obj, 568 double *&rowlb, double *&rowub); 569 570 /** Load in an problem by copying the arguments (the constraints on the 571 rows are given by sense/rhs/range triplets). If a pointer is 0 then the 572 following values are the default: 573 <ul> 574 <li> <code>colub</code>: all columns have upper bound infinity 575 <li> <code>collb</code>: all columns have lower bound 0 576 <li> <code>obj</code>: all variables have 0 objective coefficient 577 <li> <code>rowsen</code>: all rows are >= 578 <li> <code>rowrhs</code>: all right hand sides are 0 579 <li> <code>rowrng</code>: 0 for the ranged rows 580 </ul> 581 */ 582 virtual void loadProblem(const CoinPackedMatrix &matrix, 583 const double *collb, const double *colub, 584 const double *obj, 585 const char *rowsen, const double *rowrhs, 586 const double *rowrng); 587 588 /** Load in an problem by assuming ownership of the arguments (the 589 constraints on the rows are given by sense/rhs/range triplets). For 590 default values see the previous method. <br> 591 <strong>WARNING</strong>: The arguments passed to this method will be 592 freed using the C++ <code>delete</code> and <code>delete[]</code> 593 functions. 594 */ 595 virtual void assignProblem(CoinPackedMatrix *&matrix, 596 double *&collb, double *&colub, double *&obj, 597 char *&rowsen, double *&rowrhs, 598 double *&rowrng); 599 600 /** Just like the other loadProblem() methods except that the matrix is 601 given in a standard column major ordered format (without gaps). */ 602 virtual void loadProblem(const int numcols, const int numrows, 603 const CoinBigIndex *start, const int *index, 604 const double *value, 605 const double *collb, const double *colub, 606 const double *obj, 607 const double *rowlb, const double *rowub); 608 609 /** Just like the other loadProblem() methods except that the matrix is 610 given in a standard column major ordered format (without gaps). */ 611 virtual void loadProblem(const int numcols, const int numrows, 612 const CoinBigIndex *start, const int *index, 613 const double *value, 614 const double *collb, const double *colub, 615 const double *obj, 616 const char *rowsen, const double *rowrhs, 617 const double *rowrng); 618 619 using OsiSolverInterface::readMps; 620 /** Read an mps file from the given filename (defaults to Osi reader) - returns 621 number of errors (see OsiMpsReader class) */ 622 virtual int readMps(const char *filename, 623 const char *extension = "mps"); 624 625 /** Write the problem into an mps file of the given filename. 626 If objSense is non zero then -1.0 forces the code to write a 627 maximization objective and +1.0 to write a minimization one. 628 If 0.0 then solver can do what it wants */ 629 virtual void writeMps(const char *filename, 630 const char *extension = "mps", 631 double objSense = 0.0) const; 632 /** Write the problem into an mps file of the given filename, 633 names may be null. formatType is 634 0 - normal 635 1 - extra accuracy 636 2 - IEEE hex (later) 637 638 Returns non-zero on I/O error 639 */ 640 virtual int writeMpsNative(const char *filename, 641 const char **rowNames, const char **columnNames, 642 int formatType = 0, int numberAcross = 2, 643 double objSense = 0.0) const; 644 //@} 645 646 /**@name Message handling (extra for Cbc messages). 647 Normally I presume you would want the same language. 648 If not then you could use underlying model pointer */ 649 //@{ 650 /// Set language 651 void newLanguage(CoinMessages::Language language); setLanguage(CoinMessages::Language language)652 void setLanguage(CoinMessages::Language language) 653 { 654 newLanguage(language); 655 } 656 //@} 657 //--------------------------------------------------------------------------- 658 659 /**@name Cbc specific public interfaces */ 660 //@{ 661 /// Get pointer to Cbc model getModelPtr() const662 inline CbcModel *getModelPtr() const 663 { 664 return modelPtr_; 665 } 666 /// Get pointer to underlying solver getRealSolverPtr() const667 inline OsiSolverInterface *getRealSolverPtr() const 668 { 669 return modelPtr_->solver(); 670 } 671 /// Set cutoff bound on the objective function. setCutoff(double value)672 inline void setCutoff(double value) 673 { 674 modelPtr_->setCutoff(value); 675 } 676 /// Get the cutoff bound on the objective function - always as minimize getCutoff() const677 inline double getCutoff() const 678 { 679 return modelPtr_->getCutoff(); 680 } 681 /// Set the CbcModel::CbcMaxNumNode maximum node limit setMaximumNodes(int value)682 inline void setMaximumNodes(int value) 683 { 684 modelPtr_->setMaximumNodes(value); 685 } 686 /// Get the CbcModel::CbcMaxNumNode maximum node limit getMaximumNodes() const687 inline int getMaximumNodes() const 688 { 689 return modelPtr_->getMaximumNodes(); 690 } 691 /// Set the CbcModel::CbcMaxNumSol maximum number of solutions setMaximumSolutions(int value)692 inline void setMaximumSolutions(int value) 693 { 694 modelPtr_->setMaximumSolutions(value); 695 } 696 /// Get the CbcModel::CbcMaxNumSol maximum number of solutions getMaximumSolutions() const697 inline int getMaximumSolutions() const 698 { 699 return modelPtr_->getMaximumSolutions(); 700 } 701 /// Set the CbcModel::CbcMaximumSeconds maximum number of seconds setMaximumSeconds(double value)702 inline void setMaximumSeconds(double value) 703 { 704 modelPtr_->setMaximumSeconds(value); 705 } 706 /// Get the CbcModel::CbcMaximumSeconds maximum number of seconds getMaximumSeconds() const707 inline double getMaximumSeconds() const 708 { 709 return modelPtr_->getMaximumSeconds(); 710 } 711 /// Node limit reached? isNodeLimitReached() const712 inline bool isNodeLimitReached() const 713 { 714 return modelPtr_->isNodeLimitReached(); 715 } 716 /// Solution limit reached? isSolutionLimitReached() const717 inline bool isSolutionLimitReached() const 718 { 719 return modelPtr_->isSolutionLimitReached(); 720 } 721 /// Get how many Nodes it took to solve the problem. getNodeCount() const722 inline int getNodeCount() const 723 { 724 return modelPtr_->getNodeCount(); 725 } 726 /// Final status of problem - 0 finished, 1 stopped, 2 difficulties status() const727 inline int status() const 728 { 729 return modelPtr_->status(); 730 } 731 /** Pass in a message handler 732 733 It is the client's responsibility to destroy a message handler installed 734 by this routine; it will not be destroyed when the solver interface is 735 destroyed. 736 */ 737 virtual void passInMessageHandler(CoinMessageHandler *handler); 738 //@} 739 740 //--------------------------------------------------------------------------- 741 742 /**@name Constructors and destructors */ 743 //@{ 744 /// Default Constructor 745 OsiCbcSolverInterface(OsiSolverInterface *solver = NULL, 746 CbcStrategy *strategy = NULL); 747 748 /// Clone 749 virtual OsiSolverInterface *clone(bool copyData = true) const; 750 751 /// Copy constructor 752 OsiCbcSolverInterface(const OsiCbcSolverInterface &); 753 #if 0 754 /// Borrow constructor - only delete one copy 755 OsiCbcSolverInterface (CbcModel * rhs, bool reallyOwn=false); 756 757 /// Releases so won't error 758 void releaseCbc(); 759 #endif 760 /// Assignment operator 761 OsiCbcSolverInterface &operator=(const OsiCbcSolverInterface &rhs); 762 763 /// Destructor 764 virtual ~OsiCbcSolverInterface(); 765 766 //@} 767 //--------------------------------------------------------------------------- 768 769 protected: 770 ///@name Protected methods 771 //@{ 772 /** Apply a row cut (append to constraint matrix). */ 773 virtual void applyRowCut(const OsiRowCut &rc); 774 775 /** Apply a column cut (adjust one or more bounds). */ 776 virtual void applyColCut(const OsiColCut &cc); 777 //@} 778 /**@name Protected member data */ 779 //@{ 780 /// Cbc model represented by this class instance 781 mutable CbcModel *modelPtr_; 782 //@} 783 }; 784 // So unit test can find out if NDEBUG set 785 bool OsiCbcHasNDEBUG(); 786 787 //############################################################################# 788 /** A function that tests the methods in the OsiCbcSolverInterface class. */ 789 void OsiCbcSolverInterfaceUnitTest(const std::string &mpsDir, const std::string &netlibDir); 790 791 #endif 792