00001
00002
00003 #ifndef OsiSolverInterface_H
00004 #define OsiSolverInterface_H
00005
00006 #include <string>
00007 #include <vector>
00008
00009 #include "CoinMessageHandler.hpp"
00010 #include "CoinPackedVectorBase.hpp"
00011
00012 #include "OsiCollections.hpp"
00013 #include "OsiSolverParameters.hpp"
00014
00015 class CoinPackedMatrix;
00016 class CoinWarmStart;
00017
00018 class OsiCuts;
00019 class OsiAuxInfo;
00020 class OsiRowCut;
00021 class OsiRowCutDebugger;
00022 class CoinSet;
00023 class CoinBuild;
00024 class CoinModel;
00025 class OsiSolverBranch;
00026 class OsiSolverResult;
00027 #include "CoinFinite.hpp"
00028
00029
00030
00054 class OsiSolverInterface {
00055 friend void OsiSolverInterfaceCommonUnitTest(
00056 const OsiSolverInterface* emptySi,
00057 const std::string & mpsDir,
00058 const std::string & netlibDir);
00059 friend void OsiSolverInterfaceMpsUnitTest(
00060 const std::vector<OsiSolverInterface*> & vecSiP,
00061 const std::string & mpsDir);
00062
00063 public:
00065 class ApplyCutsReturnCode {
00066 friend class OsiSolverInterface;
00067 friend class OsiOslSolverInterface;
00068
00069 public:
00071
00072
00073 ApplyCutsReturnCode():
00074 intInconsistent_(0),
00075 extInconsistent_(0),
00076 infeasible_(0),
00077 ineffective_(0),
00078 applied_(0) {}
00080 ApplyCutsReturnCode(const ApplyCutsReturnCode & rhs):
00081 intInconsistent_(rhs.intInconsistent_),
00082 extInconsistent_(rhs.extInconsistent_),
00083 infeasible_(rhs.infeasible_),
00084 ineffective_(rhs.ineffective_),
00085 applied_(rhs.applied_) {}
00087 ApplyCutsReturnCode & operator=(const ApplyCutsReturnCode& rhs)
00088 {
00089 if (this != &rhs) {
00090 intInconsistent_ = rhs.intInconsistent_;
00091 extInconsistent_ = rhs.extInconsistent_;
00092 infeasible_ = rhs.infeasible_;
00093 ineffective_ = rhs.ineffective_;
00094 applied_ = rhs.applied_;
00095 }
00096 return *this;
00097 }
00099 ~ApplyCutsReturnCode(){}
00101
00104
00105 inline int getNumInconsistent(){return intInconsistent_;}
00107 inline int getNumInconsistentWrtIntegerModel(){return extInconsistent_;}
00109 inline int getNumInfeasible(){return infeasible_;}
00111 inline int getNumIneffective(){return ineffective_;}
00113 inline int getNumApplied(){return applied_;}
00115
00116 private:
00119
00120 inline void incrementInternallyInconsistent(){intInconsistent_++;}
00122 inline void incrementExternallyInconsistent(){extInconsistent_++;}
00124 inline void incrementInfeasible(){infeasible_++;}
00126 inline void incrementIneffective(){ineffective_++;}
00128 inline void incrementApplied(){applied_++;}
00130
00132
00133
00134 int intInconsistent_;
00136 int extInconsistent_;
00138 int infeasible_;
00140 int ineffective_;
00142 int applied_;
00144 };
00145
00146
00147
00148 public:
00150
00151
00152 virtual void initialSolve() = 0;
00153
00155 virtual void resolve() = 0;
00156
00158 virtual void branchAndBound() = 0;
00159
00177 #ifdef CBC_NEXT_VERSION
00178 virtual int solveBranches(int depth,const OsiSolverBranch * branch,
00179 OsiSolverResult * result,
00180 int & numberSolves, int & numberIterations,
00181 bool forceBranch=false);
00182 #endif
00183
00184
00185
00242
00243 virtual bool setIntParam(OsiIntParam key, int value) {
00244 if (key == OsiLastIntParam) return (false) ;
00245 intParam_[key] = value;
00246 return true;
00247 }
00248
00249 virtual bool setDblParam(OsiDblParam key, double value) {
00250 if (key == OsiLastDblParam) return (false) ;
00251 dblParam_[key] = value;
00252 return true;
00253 }
00254
00255 virtual bool setStrParam(OsiStrParam key, const std::string & value) {
00256 if (key == OsiLastStrParam) return (false) ;
00257 strParam_[key] = value;
00258 return true;
00259 }
00260
00261 virtual bool setHintParam(OsiHintParam key, bool yesNo=true,
00262 OsiHintStrength strength=OsiHintTry,
00263 void * otherInformation=NULL) {
00264 if (key==OsiLastHintParam)
00265 return false;
00266 hintParam_[key] = yesNo;
00267 hintStrength_[key] = strength;
00268 if (strength == OsiForceDo)
00269 throw CoinError("OsiForceDo illegal",
00270 "setHintParam", "OsiSolverInterface");
00271 return true;
00272 }
00273
00274 virtual bool getIntParam(OsiIntParam key, int& value) const {
00275 if (key == OsiLastIntParam) return (false) ;
00276 value = intParam_[key];
00277 return true;
00278 }
00279
00280 virtual bool getDblParam(OsiDblParam key, double& value) const {
00281 if (key == OsiLastDblParam) return (false) ;
00282 value = dblParam_[key];
00283 return true;
00284 }
00285
00286 virtual bool getStrParam(OsiStrParam key, std::string& value) const {
00287 if (key == OsiLastStrParam) return (false) ;
00288 value = strParam_[key];
00289 return true;
00290 }
00291
00292 virtual bool getHintParam(OsiHintParam key, bool& yesNo,
00293 OsiHintStrength& strength,
00294 void *& otherInformation) const {
00295 if (key==OsiLastHintParam)
00296 return false;
00297 yesNo = hintParam_[key];
00298 strength = hintStrength_[key];
00299 otherInformation=NULL;
00300 return true;
00301 }
00302
00303 virtual bool getHintParam(OsiHintParam key, bool& yesNo,
00304 OsiHintStrength& strength) const {
00305 if (key==OsiLastHintParam)
00306 return false;
00307 yesNo = hintParam_[key];
00308 strength = hintStrength_[key];
00309 return true;
00310 }
00311
00312 virtual bool getHintParam(OsiHintParam key, bool& yesNo) const {
00313 if (key==OsiLastHintParam)
00314 return false;
00315 yesNo = hintParam_[key];
00316 return true;
00317 }
00318
00319 void copyParameters(OsiSolverInterface & rhs);
00321
00322
00324
00325
00326 virtual bool isAbandoned() const = 0;
00328 virtual bool isProvenOptimal() const = 0;
00330 virtual bool isProvenPrimalInfeasible() const = 0;
00332 virtual bool isProvenDualInfeasible() const = 0;
00334 virtual bool isPrimalObjectiveLimitReached() const = 0;
00336 virtual bool isDualObjectiveLimitReached() const = 0;
00338 virtual bool isIterationLimitReached() const = 0;
00340
00341
00359 virtual CoinWarmStart *getEmptyWarmStart () const = 0 ;
00360
00367 virtual CoinWarmStart* getWarmStart() const = 0;
00368
00376 virtual bool setWarmStart(const CoinWarmStart* warmstart) = 0;
00378
00379
00400
00401 virtual void markHotStart();
00403 virtual void solveFromHotStart();
00405 virtual void unmarkHotStart();
00407
00408
00419
00420 virtual int getNumCols() const = 0;
00421
00423 virtual int getNumRows() const = 0;
00424
00426 virtual int getNumElements() const = 0;
00427
00429 virtual const double * getColLower() const = 0;
00430
00432 virtual const double * getColUpper() const = 0;
00433
00443 virtual const char * getRowSense() const = 0;
00444
00457 virtual const double * getRightHandSide() const = 0;
00458
00467 virtual const double * getRowRange() const = 0;
00468
00470 virtual const double * getRowLower() const = 0;
00471
00473 virtual const double * getRowUpper() const = 0;
00474
00476 virtual const double * getObjCoefficients() const = 0;
00477
00479 virtual double getObjSense() const = 0;
00480
00482 virtual bool isContinuous(int colIndex) const = 0;
00483
00485 virtual bool isBinary(int colIndex) const;
00486
00491 virtual bool isInteger(int colIndex) const;
00492
00494 virtual bool isIntegerNonBinary(int colIndex) const;
00495
00497 virtual bool isFreeBinary(int colIndex) const;
00498 #if 0
00499
00500 virtual std::string getRowName(int rowIndex) const;
00501
00503 virtual std::string getColName(int colIndex) const;
00504 #endif
00505
00507 virtual const CoinPackedMatrix * getMatrixByRow() const = 0;
00508
00510 virtual const CoinPackedMatrix * getMatrixByCol() const = 0;
00511
00513 virtual double getInfinity() const = 0;
00515
00518
00519 virtual const double * getColSolution() const = 0;
00520
00522 virtual const double * getRowPrice() const = 0;
00523
00525 virtual const double * getReducedCost() const = 0;
00526
00529 virtual const double * getRowActivity() const = 0;
00530
00532 virtual double getObjValue() const = 0;
00533
00536 virtual int getIterationCount() const = 0;
00537
00551 virtual std::vector<double*> getDualRays(int maxNumRays) const = 0;
00563 virtual std::vector<double*> getPrimalRays(int maxNumRays) const = 0;
00564
00567 virtual OsiVectorInt getFractionalIndices(const double etol=1.e-05)
00568 const;
00570
00571
00584 virtual void setObjCoeff( int elementIndex, double elementValue ) = 0;
00585
00587 virtual void setObjCoeffSet(const int* indexFirst,
00588 const int* indexLast,
00589 const double* coeffList);
00590
00593 virtual void setColLower( int elementIndex, double elementValue ) = 0;
00594
00597 virtual void setColUpper( int elementIndex, double elementValue ) = 0;
00598
00602 virtual void setColBounds( int elementIndex,
00603 double lower, double upper ) {
00604 setColLower(elementIndex, lower);
00605 setColUpper(elementIndex, upper);
00606 }
00607
00614 virtual void setColSetBounds(const int* indexFirst,
00615 const int* indexLast,
00616 const double* boundList);
00617
00620 virtual void setRowLower( int elementIndex, double elementValue ) = 0;
00621
00624 virtual void setRowUpper( int elementIndex, double elementValue ) = 0;
00625
00629 virtual void setRowBounds( int elementIndex,
00630 double lower, double upper ) {
00631 setRowLower(elementIndex, lower);
00632 setRowUpper(elementIndex, upper);
00633 }
00634
00636 virtual void setRowType(int index, char sense, double rightHandSide,
00637 double range) = 0;
00638
00643 virtual void setRowSetBounds(const int* indexFirst,
00644 const int* indexLast,
00645 const double* boundList);
00646
00651 virtual void setRowSetTypes(const int* indexFirst,
00652 const int* indexLast,
00653 const char* senseList,
00654 const double* rhsList,
00655 const double* rangeList);
00656 #if 0
00657
00658 virtual void setRowName(int rowIndex, std::string & name) {};
00659
00661 virtual void setColName(int colIndex, std::string & name) {};
00662 #endif
00665 virtual void setObjSense(double s) = 0;
00666
00676 virtual void setColSolution(const double *colsol) = 0;
00677
00688 virtual void setRowPrice(const double * rowprice) = 0;
00689
00694 virtual void setObjective(const double * array);
00695
00700 virtual void setColLower(const double * array);
00701
00706 virtual void setColUpper(const double * array);
00708
00709
00713 virtual void setContinuous(int index) = 0;
00715 virtual void setInteger(int index) = 0;
00718 virtual void setContinuous(const int* indices, int len);
00721 virtual void setInteger(const int* indices, int len);
00723
00724
00725
00733 virtual void addCol(const CoinPackedVectorBase& vec,
00734 const double collb, const double colub,
00735 const double obj) = 0;
00741 virtual void addCols(const int numcols,
00742 const CoinPackedVectorBase * const * cols,
00743 const double* collb, const double* colub,
00744 const double* obj);
00746 virtual void addCol(int numberElements, const int * rows, const double * elements,
00747 const double collb, const double colub,
00748 const double obj) ;
00754 virtual void addCols(const int numcols,
00755 const int * columnStarts, const int * rows, const double * elements,
00756 const double* collb, const double* colub,
00757 const double* obj);
00759 void addCols(const CoinBuild & buildObject);
00765 int addCols(CoinModel & modelObject);
00766 #if 0
00767
00768 virtual void addCols(const CoinPackedMatrix& matrix,
00769 const double* collb, const double* colub,
00770 const double* obj);
00771 #endif
00772
00778 virtual void deleteCols(const int num, const int * colIndices) = 0;
00779
00781 virtual void addRow(const CoinPackedVectorBase& vec,
00782 const double rowlb, const double rowub) = 0;
00784 virtual void addRow(const CoinPackedVectorBase& vec,
00785 const char rowsen, const double rowrhs,
00786 const double rowrng) = 0;
00792 virtual void addRows(const int numrows,
00793 const CoinPackedVectorBase * const * rows,
00794 const double* rowlb, const double* rowub);
00800 virtual void addRows(const int numrows,
00801 const CoinPackedVectorBase * const * rows,
00802 const char* rowsen, const double* rowrhs,
00803 const double* rowrng);
00805 virtual void addRow(int numberElements, const int * columns, const double * element,
00806 const double rowlb, const double rowub) ;
00812 virtual void addRows(const int numrows,
00813 const int * rowStarts, const int * columns, const double * element,
00814 const double* rowlb, const double* rowub);
00816 void addRows(const CoinBuild & buildObject);
00823 int addRows(CoinModel & modelObject);
00824 #if 0
00825
00826 virtual void addRows(const CoinPackedMatrix& matrix,
00827 const double* rowlb, const double* rowub);
00829 virtual void addRows(const CoinPackedMatrix& matrix,
00830 const char* rowsen, const double* rowrhs,
00831 const double* rowrng);
00832 #endif
00833
00838 virtual void deleteRows(const int num, const int * rowIndices) = 0;
00839
00840
00863 virtual ApplyCutsReturnCode applyCuts(const OsiCuts & cs,
00864 double effectivenessLb = 0.0);
00869 virtual void applyRowCuts(int numberCuts, const OsiRowCut * cuts);
00873 virtual void applyRowCuts(int numberCuts, const OsiRowCut ** cuts);
00875
00876
00877
00891 virtual void loadProblem(const CoinPackedMatrix& matrix,
00892 const double* collb, const double* colub,
00893 const double* obj,
00894 const double* rowlb, const double* rowub) = 0;
00895
00905 virtual void assignProblem(CoinPackedMatrix*& matrix,
00906 double*& collb, double*& colub, double*& obj,
00907 double*& rowlb, double*& rowub) = 0;
00908
00921 virtual void loadProblem(const CoinPackedMatrix& matrix,
00922 const double* collb, const double* colub,
00923 const double* obj,
00924 const char* rowsen, const double* rowrhs,
00925 const double* rowrng) = 0;
00926
00936 virtual void assignProblem(CoinPackedMatrix*& matrix,
00937 double*& collb, double*& colub, double*& obj,
00938 char*& rowsen, double*& rowrhs,
00939 double*& rowrng) = 0;
00940
00943 virtual void loadProblem(const int numcols, const int numrows,
00944 const CoinBigIndex * start, const int* index,
00945 const double* value,
00946 const double* collb, const double* colub,
00947 const double* obj,
00948 const double* rowlb, const double* rowub) = 0;
00949
00952 virtual void loadProblem(const int numcols, const int numrows,
00953 const CoinBigIndex * start, const int* index,
00954 const double* value,
00955 const double* collb, const double* colub,
00956 const double* obj,
00957 const char* rowsen, const double* rowrhs,
00958 const double* rowrng) = 0;
00964 virtual int loadFromCoinModel ( CoinModel & modelObject, bool keepSolution=false);
00965
00971 virtual int readMps(const char *filename,
00972 const char *extension = "mps") ;
00973
00980 virtual int readMps(const char *filename, const char*extension,
00981 int & numberSets, CoinSet ** & sets);
00982
00987 virtual int readGMPL(const char *filename, const char * dataname=NULL);
00994 virtual void writeMps(const char *filename,
00995 const char *extension = "mps",
00996 double objSense=0.0) const = 0;
00997
01010 int writeMpsNative(const char *filename,
01011 const char ** rowNames, const char ** columnNames,
01012 int formatType=0,int numberAcross=2,
01013 double objSense=0.0) const ;
01014
01015
01016
01017
01037 virtual void writeLp(const char *filename,
01038 const char *extension = "lp",
01039 const double epsilon = 1e-5,
01040 const int numberAcross = 10,
01041 const int decimals = 5,
01042 const double objSense = 0.0,
01043 const bool useRowNames = true) const;
01044
01049 virtual void writeLp(FILE *fp,
01050 const double epsilon = 1e-5,
01051 const int numberAcross = 10,
01052 const int decimals = 5,
01053 const double objSense = 0.0,
01054 const bool useRowNames = true) const;
01055
01074 int writeLpNative(const char *filename,
01075 char const * const * const rowNames,
01076 char const * const * const columnNames,
01077 const double epsilon = 1.0e-5,
01078 const int numberAcross = 10,
01079 const int decimals = 5,
01080 const double objSense = 0.0,
01081 const bool useRowNames = true) const;
01082
01087 int writeLpNative(FILE *fp,
01088 char const * const * const rowNames,
01089 char const * const * const columnNames,
01090 const double epsilon = 1.0e-5,
01091 const int numberAcross = 10,
01092 const int decimals = 5,
01093 const double objSense = 0.0,
01094 const bool useRowNames = true) const;
01095
01098 virtual int readLp(const char *filename, const double epsilon = 1e-5);
01099
01102 int readLp(FILE *fp, const double epsilon = 1e-5);
01103
01109 virtual void replaceMatrixOptional(const CoinPackedMatrix & matrix) {};
01111 virtual void replaceMatrix(const CoinPackedMatrix & matrix) {abort();};
01113
01114
01115
01125 void setApplicationData (void * appData);
01132 void setAuxiliaryInfo(OsiAuxInfo * auxiliaryInfo);
01133
01135 void * getApplicationData() const;
01137 OsiAuxInfo * getAuxiliaryInfo() const;
01139
01140
01154 void passInMessageHandler(CoinMessageHandler * handler);
01156 void newLanguage(CoinMessages::Language language);
01157 void setLanguage(CoinMessages::Language language)
01158 {newLanguage(language);};
01160 CoinMessageHandler * messageHandler() const
01161 {return handler_;};
01163 CoinMessages messages()
01164 {return messages_;};
01166 CoinMessages * messagesPointer()
01167 {return &messages_;};
01169
01170
01179 virtual void activateRowCutDebugger (const char * modelName);
01180
01186 virtual void activateRowCutDebugger( const double * solution);
01196 const OsiRowCutDebugger * getRowCutDebugger() const;
01198 const OsiRowCutDebugger * getRowCutDebuggerAlways() const;
01199
01201
01202
01210 public:
01212
01213
01216 virtual int canDoSimplexInterface() const;
01223 virtual void enableSimplexInterface(bool doingPrimal) ;
01224
01226 virtual void disableSimplexInterface() ;
01227
01234 virtual void enableFactorization() const;
01236 virtual void disableFactorization() const;
01237
01242 virtual bool basisIsAvailable() const ;
01244 inline bool optimalBasisIsAvailable() const
01245 { return basisIsAvailable();};
01246
01259 virtual void getBasisStatus(int* cstat, int* rstat) const ;
01260
01267 virtual int setBasisStatus(const int* cstat, const int* rstat) ;
01268
01276 virtual int pivot(int colIn, int colOut, int outStatus) ;
01277
01289 virtual int primalPivotResult(int colIn, int sign,
01290 int& colOut, int& outStatus,
01291 double& t, CoinPackedVector* dx);
01292
01299 virtual int dualPivotResult(int& colIn, int& sign,
01300 int colOut, int outStatus,
01301 double& t, CoinPackedVector* dx) ;
01302
01304 virtual void getReducedGradient(double* columnReducedCosts,
01305 double * duals,
01306 const double * c) ;
01307
01310 virtual void setObjectiveAndRefresh(double* c) ;
01311
01313 virtual void getBInvARow(int row, double* z, double * slack=NULL) const ;
01314
01316 virtual void getBInvRow(int row, double* z) const ;
01317
01319 virtual void getBInvACol(int col, double* vec) const ;
01320
01322 virtual void getBInvCol(int col, double* vec) const ;
01323
01328 virtual void getBasics(int* index) const ;
01330
01331
01332
01334
01335
01336 OsiSolverInterface();
01337
01343 virtual OsiSolverInterface * clone(bool copyData = true) const = 0;
01344
01346 OsiSolverInterface(const OsiSolverInterface &);
01347
01349 OsiSolverInterface & operator=(const OsiSolverInterface& rhs);
01350
01352 virtual ~OsiSolverInterface ();
01353
01360 virtual void reset();
01362
01363
01364
01365 protected:
01367
01368
01369 virtual void applyRowCut( const OsiRowCut & rc ) = 0;
01370
01372 virtual void applyColCut( const OsiColCut & cc ) = 0;
01373
01376 inline void
01377 convertBoundToSense(const double lower, const double upper,
01378 char& sense, double& right, double& range) const;
01381 inline void
01382 convertSenseToBound(const char sense, const double right,
01383 const double range,
01384 double& lower, double& upper) const;
01387 template <class T> inline T
01388 forceIntoRange(const T value, const T lower, const T upper) const {
01389 return value < lower ? lower : (value > upper ? upper : value);
01390 }
01397 void setInitialData();
01399
01401
01402
01403 OsiRowCutDebugger * rowCutDebugger_;
01405
01406
01407
01408 private:
01410
01411
01412 OsiAuxInfo * appDataEtc_;
01414 int intParam_[OsiLastIntParam];
01416 double dblParam_[OsiLastDblParam];
01418 std::string strParam_[OsiLastStrParam];
01420 bool hintParam_[OsiLastHintParam];
01422 OsiHintStrength hintStrength_[OsiLastHintParam];
01425 CoinWarmStart* ws_;
01426
01427 protected:
01429 CoinMessageHandler * handler_;
01435 bool defaultHandler_;
01437 CoinMessages messages_;
01439 };
01440
01441
01449 void
01450 OsiSolverInterfaceCommonUnitTest(
01451 const OsiSolverInterface* emptySi,
01452 const std::string & mpsDir,
01453 const std::string & netlibDir);
01454
01455
01458 void
01459 OsiSolverInterfaceMpsUnitTest(
01460 const std::vector<OsiSolverInterface*> & vecSiP,
01461 const std::string & mpsDir);
01462
01463
01466 inline void
01467 OsiSolverInterface::convertBoundToSense(const double lower, const double upper,
01468 char& sense, double& right,
01469 double& range) const
01470 {
01471 double inf = getInfinity();
01472 range = 0.0;
01473 if (lower > -inf) {
01474 if (upper < inf) {
01475 right = upper;
01476 if (upper==lower) {
01477 sense = 'E';
01478 } else {
01479 sense = 'R';
01480 range = upper - lower;
01481 }
01482 } else {
01483 sense = 'G';
01484 right = lower;
01485 }
01486 } else {
01487 if (upper < inf) {
01488 sense = 'L';
01489 right = upper;
01490 } else {
01491 sense = 'N';
01492 right = 0.0;
01493 }
01494 }
01495 }
01496
01497
01500 inline void
01501 OsiSolverInterface::convertSenseToBound(const char sense, const double right,
01502 const double range,
01503 double& lower, double& upper) const
01504 {
01505 double inf=getInfinity();
01506 switch (sense) {
01507 case 'E':
01508 lower = upper = right;
01509 break;
01510 case 'L':
01511 lower = -inf;
01512 upper = right;
01513 break;
01514 case 'G':
01515 lower = right;
01516 upper = inf;
01517 break;
01518 case 'R':
01519 lower = right - range;
01520 upper = right;
01521 break;
01522 case 'N':
01523 lower = -inf;
01524 upper = inf;
01525 break;
01526 }
01527 }
01528
01529 #endif