00001
00002
00003
00004
00005
00006
00007 #ifndef OsiClpSolverInterface_H
00008 #define OsiClpSolverInterface_H
00009
00010 #include <string>
00011 #include <cfloat>
00012 #include <map>
00013
00014 #include "ClpSimplex.hpp"
00015 #include "ClpLinearObjective.hpp"
00016 #include "CoinPackedMatrix.hpp"
00017 #include "OsiSolverInterface.hpp"
00018 #include "CoinWarmStartBasis.hpp"
00019 #include "ClpEventHandler.hpp"
00020 #include "ClpNode.hpp"
00021 #include "CoinIndexedVector.hpp"
00022 #include "CoinFinite.hpp"
00023
00024 class OsiRowCut;
00025 class OsiClpUserSolver;
00026 class OsiClpDisasterHandler;
00027 class CoinSet;
00028 static const double OsiClpInfinity = COIN_DBL_MAX;
00029
00030
00031
00038 class OsiClpSolverInterface :
00039 virtual public OsiSolverInterface {
00040 friend void OsiClpSolverInterfaceUnitTest(const std::string & mpsDir, const std::string & netlibDir);
00041
00042 public:
00043
00046
00047 virtual void initialSolve();
00048
00050 virtual void resolve();
00051
00053 virtual void resolveGub(int needed);
00054
00056 virtual void branchAndBound();
00057
00065 void crossover(int options,int basis);
00067
00083 virtual int canDoSimplexInterface() const;
00084
00093 virtual void enableFactorization() const;
00094
00096 virtual void disableFactorization() const;
00097
00102 virtual bool basisIsAvailable() const;
00103
00119 virtual void getBasisStatus(int* cstat, int* rstat) const;
00120
00131 virtual int setBasisStatus(const int* cstat, const int* rstat);
00132
00134 virtual void getReducedGradient(double* columnReducedCosts,
00135 double * duals,
00136 const double * c) const ;
00137
00139 virtual void getBInvARow(int row, double* z, double * slack=NULL) const;
00140
00145 virtual void getBInvARow(int row, CoinIndexedVector * z, CoinIndexedVector * slack=NULL,
00146 bool keepScaled=false) const;
00147
00149 virtual void getBInvRow(int row, double* z) const;
00150
00152 virtual void getBInvACol(int col, double* vec) const ;
00153
00155 virtual void getBInvACol(int col, CoinIndexedVector * vec) const ;
00156
00161 virtual void getBInvACol(CoinIndexedVector * vec) const ;
00162
00164 virtual void getBInvCol(int col, double* vec) const ;
00165
00170 virtual void getBasics(int* index) const;
00171
00178 virtual void enableSimplexInterface(bool doingPrimal);
00180 void copyEnabledSuff(OsiClpSolverInterface & rhs);
00181
00183 virtual void disableSimplexInterface();
00185 void copyEnabledStuff(ClpSimplex & rhs);
00186
00194 virtual int pivot(int colIn, int colOut, int outStatus);
00195
00207 virtual int primalPivotResult(int colIn, int sign,
00208 int& colOut, int& outStatus,
00209 double& t, CoinPackedVector* dx);
00210
00217 virtual int dualPivotResult(int& colIn, int& sign,
00218 int colOut, int outStatus,
00219 double& t, CoinPackedVector* dx);
00220
00221
00223
00239
00240 bool setIntParam(OsiIntParam key, int value);
00241
00242 bool setDblParam(OsiDblParam key, double value);
00243
00244 bool setStrParam(OsiStrParam key, const std::string & value);
00245
00246 bool getIntParam(OsiIntParam key, int& value) const;
00247
00248 bool getDblParam(OsiDblParam key, double& value) const;
00249
00250 bool getStrParam(OsiStrParam key, std::string& value) const;
00251
00252 virtual bool setHintParam(OsiHintParam key, bool yesNo=true,
00253 OsiHintStrength strength=OsiHintTry,
00254 void * otherInformation=NULL);
00256
00257
00259
00260
00261 virtual bool isAbandoned() const;
00263 virtual bool isProvenOptimal() const;
00265 virtual bool isProvenPrimalInfeasible() const;
00267 virtual bool isProvenDualInfeasible() const;
00269 virtual bool isPrimalObjectiveLimitReached() const;
00271 virtual bool isDualObjectiveLimitReached() const;
00273 virtual bool isIterationLimitReached() const;
00275
00276
00279
00287 virtual CoinWarmStart *getEmptyWarmStart () const;
00288
00290 virtual CoinWarmStart* getWarmStart() const;
00292 inline CoinWarmStartBasis* getPointerToWarmStart()
00293 { return &basis_;}
00295 inline const CoinWarmStartBasis* getConstPointerToWarmStart() const
00296 { return &basis_;}
00299 virtual bool setWarmStart(const CoinWarmStart* warmstart);
00309 virtual CoinWarmStart* getPointerToWarmStart(bool & mustDelete) ;
00310
00312 void setColumnStatus(int iColumn, ClpSimplex::Status status);
00313
00315
00316
00323
00324 virtual void markHotStart();
00326 virtual void solveFromHotStart();
00328 virtual void unmarkHotStart();
00337 int startFastDual(int options);
00339 void stopFastDual();
00341 void setStuff(double tolerance,double increment);
00343 OsiRowCut * smallModelCut(const double * originalLower, const double * originalUpper,
00344 int numberRowsAtContinuous,const int * whichGenerator,
00345 int typeCut=0);
00349 OsiRowCut * modelCut(const double * originalLower, const double * originalUpper,
00350 int numberRowsAtContinuous,const int * whichGenerator,
00351 int typeCut=0);
00353
00354
00369
00370 virtual int getNumCols() const {
00371 return modelPtr_->numberColumns(); }
00372
00374 virtual int getNumRows() const {
00375 return modelPtr_->numberRows(); }
00376
00378 virtual int getNumElements() const {
00379 int retVal = 0;
00380 const CoinPackedMatrix * matrix =modelPtr_->matrix();
00381 if ( matrix != NULL ) retVal=matrix->getNumElements();
00382 return retVal; }
00383
00386 virtual std::string getRowName(int rowIndex,
00387 unsigned maxLen = static_cast<unsigned>(std::string::npos)) const;
00388
00391 virtual std::string getColName(int colIndex,
00392 unsigned maxLen = static_cast<unsigned>(std::string::npos)) const;
00393
00394
00396 virtual const double * getColLower() const { return modelPtr_->columnLower(); }
00397
00399 virtual const double * getColUpper() const { return modelPtr_->columnUpper(); }
00400
00410 virtual const char * getRowSense() const;
00411
00420 virtual const double * getRightHandSide() const ;
00421
00430 virtual const double * getRowRange() const ;
00431
00433 virtual const double * getRowLower() const { return modelPtr_->rowLower(); }
00434
00436 virtual const double * getRowUpper() const { return modelPtr_->rowUpper(); }
00437
00439 virtual const double * getObjCoefficients() const
00440 { if (fakeMinInSimplex_)
00441 return linearObjective_ ;
00442 else
00443 return modelPtr_->objective(); }
00444
00446 virtual double getObjSense() const
00447 { return ((fakeMinInSimplex_)?-modelPtr_->optimizationDirection():
00448 modelPtr_->optimizationDirection()); }
00449
00451 virtual bool isContinuous(int colNumber) const;
00453 virtual bool isBinary(int colIndex) const;
00454
00459 virtual bool isInteger(int colIndex) const;
00460
00462 virtual bool isIntegerNonBinary(int colIndex) const;
00463
00465 virtual bool isFreeBinary(int colIndex) const;
00471 virtual const char * getColType(bool refresh=false) const;
00472
00478 bool isOptionalInteger(int colIndex) const;
00480 void setOptionalInteger(int index);
00481
00483 virtual const CoinPackedMatrix * getMatrixByRow() const;
00484
00486 virtual const CoinPackedMatrix * getMatrixByCol() const;
00487
00489 virtual CoinPackedMatrix * getMutableMatrixByCol() const;
00490
00492 virtual double getInfinity() const { return OsiClpInfinity; }
00494
00497
00498 virtual const double * getColSolution() const;
00499
00501 virtual const double * getRowPrice() const;
00502
00504 virtual const double * getReducedCost() const;
00505
00508 virtual const double * getRowActivity() const;
00509
00511 virtual double getObjValue() const;
00512
00515 virtual int getIterationCount() const
00516 { return modelPtr_->numberIterations(); }
00517
00535 virtual std::vector<double*> getDualRays(int maxNumRays,
00536 bool fullRay = false) const;
00548 virtual std::vector<double*> getPrimalRays(int maxNumRays) const;
00549
00551
00552
00553
00554
00557
00561 virtual void setObjCoeff( int elementIndex, double elementValue );
00562
00565 virtual void setColLower( int elementIndex, double elementValue );
00566
00569 virtual void setColUpper( int elementIndex, double elementValue );
00570
00572 virtual void setColBounds( int elementIndex,
00573 double lower, double upper );
00574
00583 virtual void setColSetBounds(const int* indexFirst,
00584 const int* indexLast,
00585 const double* boundList);
00586
00589 virtual void setRowLower( int elementIndex, double elementValue );
00590
00593 virtual void setRowUpper( int elementIndex, double elementValue ) ;
00594
00596 virtual void setRowBounds( int elementIndex,
00597 double lower, double upper ) ;
00598
00600 virtual void setRowType(int index, char sense, double rightHandSide,
00601 double range);
00602
00611 virtual void setRowSetBounds(const int* indexFirst,
00612 const int* indexLast,
00613 const double* boundList);
00614
00625 virtual void setRowSetTypes(const int* indexFirst,
00626 const int* indexLast,
00627 const char* senseList,
00628 const double* rhsList,
00629 const double* rangeList);
00634 virtual void setObjective(const double * array);
00635
00640 virtual void setColLower(const double * array);
00641
00646 virtual void setColUpper(const double * array);
00647
00648
00650
00651 virtual void setRowName(int rowIndex, std::string name) ;
00652
00653
00655
00656 virtual void setColName(int colIndex, std::string name) ;
00657
00659
00660
00664 virtual void setContinuous(int index);
00666 virtual void setInteger(int index);
00669 virtual void setContinuous(const int* indices, int len);
00672 virtual void setInteger(const int* indices, int len);
00674 inline int numberSOS() const
00675 { return numberSOS_;}
00677 inline const CoinSet * setInfo() const
00678 { return setInfo_;}
00688 virtual int findIntegersAndSOS(bool justCount);
00690
00691
00693 virtual void setObjSense(double s )
00694 { modelPtr_->setOptimizationDirection( s < 0 ? -1 : 1); }
00695
00706 virtual void setColSolution(const double * colsol);
00707
00718 virtual void setRowPrice(const double * rowprice);
00719
00720
00725
00726
00728 virtual void addCol(const CoinPackedVectorBase& vec,
00729 const double collb, const double colub,
00730 const double obj);
00733 virtual void addCol(const CoinPackedVectorBase& vec,
00734 const double collb, const double colub,
00735 const double obj, std::string name) ;
00737 virtual void addCol(int numberElements, const int * rows, const double * elements,
00738 const double collb, const double colub,
00739 const double obj) ;
00742 virtual void addCol(int numberElements,
00743 const int* rows, const double* elements,
00744 const double collb, const double colub,
00745 const double obj, std::string name) ;
00747 virtual void addCols(const int numcols,
00748 const CoinPackedVectorBase * const * cols,
00749 const double* collb, const double* colub,
00750 const double* obj);
00752 virtual void addCols(const int numcols,
00753 const int * columnStarts, const int * rows, const double * elements,
00754 const double* collb, const double* colub,
00755 const double* obj);
00757 virtual void deleteCols(const int num, const int * colIndices);
00758
00760 virtual void addRow(const CoinPackedVectorBase& vec,
00761 const double rowlb, const double rowub);
00768 virtual void addRow(const CoinPackedVectorBase& vec,
00769 const double rowlb, const double rowub,
00770 std::string name) ;
00771 virtual void addRow(const CoinPackedVectorBase& vec,
00772 const char rowsen, const double rowrhs,
00773 const double rowrng);
00775 virtual void addRow(int numberElements, const int * columns, const double * element,
00776 const double rowlb, const double rowub) ;
00779 virtual void addRow(const CoinPackedVectorBase& vec,
00780 const char rowsen, const double rowrhs,
00781 const double rowrng, std::string name) ;
00783 virtual void addRows(const int numrows,
00784 const CoinPackedVectorBase * const * rows,
00785 const double* rowlb, const double* rowub);
00787 virtual void addRows(const int numrows,
00788 const CoinPackedVectorBase * const * rows,
00789 const char* rowsen, const double* rowrhs,
00790 const double* rowrng);
00791
00793 virtual void addRows(const int numrows,
00794 const int * rowStarts, const int * columns, const double * element,
00795 const double* rowlb, const double* rowub);
00797 void modifyCoefficient(int row, int column, double newElement,
00798 bool keepZero=false)
00799 {modelPtr_->modifyCoefficient(row,column,newElement, keepZero);}
00800
00802 virtual void deleteRows(const int num, const int * rowIndices);
00805 virtual void saveBaseModel() ;
00809 virtual void restoreBaseModel(int numberRows);
00810
00811
00815 virtual void applyRowCuts(int numberCuts, const OsiRowCut * cuts);
00820 virtual void applyRowCuts(int numberCuts, const OsiRowCut ** cuts);
00843 virtual ApplyCutsReturnCode applyCuts(const OsiCuts & cs,
00844 double effectivenessLb = 0.0);
00845
00847
00848
00849
00850
00851 public:
00852
00866 virtual void loadProblem(const CoinPackedMatrix& matrix,
00867 const double* collb, const double* colub,
00868 const double* obj,
00869 const double* rowlb, const double* rowub);
00870
00878 virtual void assignProblem(CoinPackedMatrix*& matrix,
00879 double*& collb, double*& colub, double*& obj,
00880 double*& rowlb, double*& rowub);
00881
00894 virtual void loadProblem(const CoinPackedMatrix& matrix,
00895 const double* collb, const double* colub,
00896 const double* obj,
00897 const char* rowsen, const double* rowrhs,
00898 const double* rowrng);
00899
00907 virtual void assignProblem(CoinPackedMatrix*& matrix,
00908 double*& collb, double*& colub, double*& obj,
00909 char*& rowsen, double*& rowrhs,
00910 double*& rowrng);
00911
00914 virtual void loadProblem(const ClpMatrixBase& matrix,
00915 const double* collb, const double* colub,
00916 const double* obj,
00917 const double* rowlb, const double* rowub) ;
00918
00921 virtual void loadProblem(const int numcols, const int numrows,
00922 const CoinBigIndex * start, const int* index,
00923 const double* value,
00924 const double* collb, const double* colub,
00925 const double* obj,
00926 const double* rowlb, const double* rowub);
00927
00930 virtual void loadProblem(const int numcols, const int numrows,
00931 const CoinBigIndex * start, const int* index,
00932 const double* value,
00933 const double* collb, const double* colub,
00934 const double* obj,
00935 const char* rowsen, const double* rowrhs,
00936 const double* rowrng);
00938 virtual int loadFromCoinModel ( CoinModel & modelObject, bool keepSolution=false);
00939
00940 using OsiSolverInterface::readMps ;
00943 virtual int readMps(const char *filename,
00944 const char *extension = "mps") ;
00947 int readMps(const char *filename,bool keepNames,bool allowErrors);
00949 virtual int readMps (const char *filename, const char*extension,
00950 int & numberSets, CoinSet ** & sets);
00951
00956 virtual void writeMps(const char *filename,
00957 const char *extension = "mps",
00958 double objSense=0.0) const;
00967 virtual int writeMpsNative(const char *filename,
00968 const char ** rowNames, const char ** columnNames,
00969 int formatType=0,int numberAcross=2,
00970 double objSense=0.0) const ;
00972 virtual int readLp(const char *filename, const double epsilon = 1e-5);
00978 virtual void writeLp(const char *filename,
00979 const char *extension = "lp",
00980 double epsilon = 1e-5,
00981 int numberAcross = 10,
00982 int decimals = 5,
00983 double objSense = 0.0,
00984 bool useRowNames = true) const;
00989 virtual void writeLp(FILE *fp,
00990 double epsilon = 1e-5,
00991 int numberAcross = 10,
00992 int decimals = 5,
00993 double objSense = 0.0,
00994 bool useRowNames = true) const;
01000 virtual void replaceMatrixOptional(const CoinPackedMatrix & matrix);
01002 virtual void replaceMatrix(const CoinPackedMatrix & matrix) ;
01004
01015 virtual void passInMessageHandler(CoinMessageHandler * handler);
01017 void newLanguage(CoinMessages::Language language);
01018 void setLanguage(CoinMessages::Language language)
01019 {newLanguage(language);}
01021 void setLogLevel(int value);
01023 void generateCpp( FILE * fp);
01025
01026
01029
01030 ClpSimplex * getModelPtr() const ;
01032 inline ClpSimplex * swapModelPtr(ClpSimplex * newModel)
01033 { ClpSimplex * model = modelPtr_; modelPtr_=newModel;return model;}
01035 inline unsigned int specialOptions() const
01036 { return specialOptions_;}
01037 void setSpecialOptions(unsigned int value);
01039 inline int lastAlgorithm() const
01040 { return lastAlgorithm_;}
01042 inline void setLastAlgorithm(int value)
01043 { lastAlgorithm_ = value;}
01045 inline int cleanupScaling() const
01046 { return cleanupScaling_;}
01059 inline void setCleanupScaling(int value)
01060 { cleanupScaling_=value;}
01063 inline double smallestElementInCut() const
01064 { return smallestElementInCut_;}
01067 inline void setSmallestElementInCut(double value)
01068 { smallestElementInCut_=value;}
01075 inline double smallestChangeInCut() const
01076 { return smallestChangeInCut_;}
01083 inline void setSmallestChangeInCut(double value)
01084 { smallestChangeInCut_=value;}
01086 inline void setSolveOptions(const ClpSolve & options)
01087 { solveOptions_ = options;}
01091 virtual int tightenBounds(int lightweight=0);
01093 int infeasibleOtherWay(char * whichWay);
01095 virtual CoinBigIndex getSizeL() const;
01097 virtual CoinBigIndex getSizeU() const;
01099 const OsiClpDisasterHandler * disasterHandler() const
01100 { return disasterHandler_;}
01102 void passInDisasterHandler(OsiClpDisasterHandler * handler);
01104 ClpLinearObjective * fakeObjective() const
01105 { return fakeObjective_;}
01107 void setFakeObjective(ClpLinearObjective * fakeObjective);
01109 void setFakeObjective(double * fakeObjective);
01129 void setupForRepeatedUse(int senseOfAdventure=0, int printOut=0);
01131 virtual void synchronizeModel();
01136 void setSpecialOptionsMutable(unsigned int value) const;
01137
01139
01140
01141
01144
01145 OsiClpSolverInterface ();
01146
01148 virtual OsiSolverInterface * clone(bool copyData = true) const;
01149
01151 OsiClpSolverInterface (const OsiClpSolverInterface &);
01152
01154 OsiClpSolverInterface (ClpSimplex * rhs, bool reallyOwn=false);
01155
01157 void releaseClp();
01158
01160 OsiClpSolverInterface & operator=(const OsiClpSolverInterface& rhs);
01161
01163 virtual ~OsiClpSolverInterface ();
01164
01166 virtual void reset();
01168
01169
01170
01171 protected:
01173
01174
01175 virtual void applyRowCut(const OsiRowCut& rc);
01176
01178 virtual void applyColCut(const OsiColCut& cc);
01180
01181
01182
01183 protected:
01186
01187 void gutsOfDestructor();
01188
01190 void freeCachedResults() const;
01191
01193 void freeCachedResults0() const;
01194
01196 void freeCachedResults1() const;
01197
01199 void extractSenseRhsRange() const;
01200
01202 void fillParamMaps();
01211 CoinWarmStartBasis getBasis(ClpSimplex * model) const;
01220 void setBasis( const CoinWarmStartBasis & basis, ClpSimplex * model);
01222 void crunch();
01224 void redoScaleFactors(int numberRows,const CoinBigIndex * starts,
01225 const int * indices, const double * elements);
01226 public:
01229 void setBasis( const CoinWarmStartBasis & basis);
01231 inline void setBasis( )
01232 { setBasis(basis_,modelPtr_);}
01234 CoinWarmStartDiff * getBasisDiff(const unsigned char * statusArray) const ;
01236 CoinWarmStartBasis * getBasis(const unsigned char * statusArray) const ;
01238 void deleteScaleFactors();
01240 inline const double * upRange() const
01241 { return rowActivity_;}
01242 inline const double * downRange() const
01243 { return columnActivity_;}
01245 inline void passInRanges(int * array)
01246 { whichRange_=array;}
01248 void setSOSData(int numberSOS,const char * type,
01249 const int * start,const int * indices, const double * weights=NULL);
01251 void computeLargestAway();
01253 inline double largestAway() const
01254 { return largestAway_;}
01256 inline void setLargestAway(double value)
01257 { largestAway_ = value;}
01259 void lexSolve();
01261
01262 protected:
01265
01266 mutable ClpSimplex * modelPtr_;
01268
01270
01271 mutable char *rowsense_;
01272
01274 mutable double *rhs_;
01275
01279 mutable double *rowrange_;
01280
01283 mutable CoinWarmStartBasis* ws_;
01286 mutable double * rowActivity_;
01287 mutable double * columnActivity_;
01289 ClpNodeStuff stuff_;
01291 int numberSOS_;
01293 CoinSet * setInfo_;
01295 ClpSimplex * smallModel_;
01297 ClpFactorization * factorization_;
01300 double smallestElementInCut_;
01304 double smallestChangeInCut_;
01306 double largestAway_;
01308 char * spareArrays_;
01310 CoinWarmStartBasis basis_;
01312 int itlimOrig_;
01313
01324 mutable int lastAlgorithm_;
01325
01327 bool notOwned_;
01328
01330 mutable CoinPackedMatrix *matrixByRow_;
01331
01333 CoinPackedMatrix *matrixByRowAtContinuous_;
01334
01336 char * integerInformation_;
01337
01342 int * whichRange_;
01343
01344
01345
01346
01347
01349 mutable bool fakeMinInSimplex_ ;
01356 mutable double *linearObjective_;
01357
01359 mutable ClpDataSave saveData_;
01361 ClpSolve solveOptions_;
01374 int cleanupScaling_;
01402 mutable unsigned int specialOptions_;
01404 ClpSimplex * baseModel_;
01406 int lastNumberRows_;
01408 ClpSimplex * continuousModel_;
01410 OsiClpDisasterHandler * disasterHandler_ ;
01412 ClpLinearObjective * fakeObjective_;
01414 CoinDoubleArrayWithLength rowScale_;
01416 CoinDoubleArrayWithLength columnScale_;
01418 };
01419
01420 class OsiClpDisasterHandler : public ClpDisasterHandler {
01421 public:
01425
01426 virtual void intoSimplex();
01428 virtual bool check() const ;
01430 virtual void saveInfo();
01432 virtual int typeOfDisaster();
01434
01435
01440 OsiClpDisasterHandler(OsiClpSolverInterface * model = NULL);
01442 virtual ~OsiClpDisasterHandler();
01443
01444 OsiClpDisasterHandler(const OsiClpDisasterHandler&);
01445
01446 OsiClpDisasterHandler& operator=(const OsiClpDisasterHandler&);
01448 virtual ClpDisasterHandler * clone() const;
01449
01451
01456 void setOsiModel(OsiClpSolverInterface * model);
01458 inline OsiClpSolverInterface * osiModel() const
01459 { return osiModel_;}
01461 inline void setWhereFrom(int value)
01462 { whereFrom_=value;}
01464 inline int whereFrom() const
01465 { return whereFrom_;}
01467 inline void setPhase(int value)
01468 { phase_=value;}
01470 inline int phase() const
01471 { return phase_;}
01473 bool inTrouble() const;
01474
01476
01477
01478 protected:
01482
01483 OsiClpSolverInterface * osiModel_;
01491 int whereFrom_;
01499 int phase_;
01501 bool inTrouble_;
01503 };
01504
01505 bool OsiClpHasNDEBUG();
01506
01508 void OsiClpSolverInterfaceUnitTest(const std::string & mpsDir, const std::string & netlibDir);
01509 #endif