source: trunk/Clp/src/ClpModel.hpp @ 1141

Last change on this file since 1141 was 1141, checked in by forrest, 12 years ago

for threaded random numbers

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 39.6 KB
Line 
1// Copyright (C) 2002, International Business Machines
2// Corporation and others.  All Rights Reserved.
3#ifndef ClpModel_H
4#define ClpModel_H
5
6#include "ClpConfig.h"
7
8#include <iostream>
9#include <cassert>
10#include <cmath>
11#include <vector>
12#include <string>
13//#ifndef COIN_USE_CLP
14//#define COIN_USE_CLP
15//#endif
16#include "ClpPackedMatrix.hpp"
17#include "CoinMessageHandler.hpp"
18#include "CoinHelperFunctions.hpp"
19#include "ClpParameters.hpp"
20#include "ClpObjective.hpp"
21class ClpEventHandler;
22
23// Plus infinity
24#ifndef COIN_DBL_MAX
25#define COIN_DBL_MAX DBL_MAX
26#endif
27
28/** This is the base class for Linear and quadratic Models
29    This knows nothing about the algorithm, but it seems to
30    have a reasonable amount of information
31
32    I would welcome suggestions for what should be in this and
33    how it relates to OsiSolverInterface.  Some methods look
34    very similar.
35
36*/
37class CoinBuild;
38class CoinModel;
39class ClpModel {
40
41public:
42
43  /**@name Constructors and destructor
44     Note - copy methods copy ALL data so can chew up memory
45     until other copy is freed
46   */
47  //@{
48    /// Default constructor
49    ClpModel (bool emptyMessages=false  );
50
51  /** Copy constructor. May scale depending on mode
52      -1 leave mode as is
53      0 -off, 1 equilibrium, 2 geometric, 3, auto, 4 auto-but-as-initialSolve-in-bab
54  */
55    ClpModel(const ClpModel & rhs, int scalingMode=-1);
56    /// Assignment operator. This copies the data
57    ClpModel & operator=(const ClpModel & rhs);
58  /** Subproblem constructor.  A subset of whole model is created from the
59      row and column lists given.  The new order is given by list order and
60      duplicates are allowed.  Name and integer information can be dropped
61  */
62    ClpModel (const ClpModel * wholeModel,
63      int numberRows, const int * whichRows,
64      int numberColumns, const int * whichColumns,
65              bool dropNames=true, bool dropIntegers=true);
66    /// Destructor
67    ~ClpModel (  );
68  //@}
69
70  /**@name Load model - loads some stuff and initializes others */
71  //@{
72    /** Loads a problem (the constraints on the
73        rows are given by lower and upper bounds). If a pointer is 0 then the
74        following values are the default:
75        <ul>
76          <li> <code>colub</code>: all columns have upper bound infinity
77          <li> <code>collb</code>: all columns have lower bound 0
78          <li> <code>rowub</code>: all rows have upper bound infinity
79          <li> <code>rowlb</code>: all rows have lower bound -infinity
80          <li> <code>obj</code>: all variables have 0 objective coefficient
81        </ul>
82    */
83  void loadProblem (  const ClpMatrixBase& matrix,
84                     const double* collb, const double* colub,   
85                     const double* obj,
86                     const double* rowlb, const double* rowub,
87                      const double * rowObjective=NULL);
88  void loadProblem (  const CoinPackedMatrix& matrix,
89                     const double* collb, const double* colub,   
90                     const double* obj,
91                     const double* rowlb, const double* rowub,
92                      const double * rowObjective=NULL);
93
94  /** Just like the other loadProblem() method except that the matrix is
95        given in a standard column major ordered format (without gaps). */
96  void loadProblem (  const int numcols, const int numrows,
97                     const CoinBigIndex* start, const int* index,
98                     const double* value,
99                     const double* collb, const double* colub,   
100                     const double* obj,
101                      const double* rowlb, const double* rowub,
102                      const double * rowObjective=NULL);
103  /** This loads a model from a coinModel object - returns number of errors.
104
105      modelObject not const as may be changed as part of process
106      If tryPlusMinusOne then will try adding as +-1 matrix
107  */
108  int loadProblem (  CoinModel & modelObject,bool tryPlusMinusOne=false);
109  /// This one is for after presolve to save memory
110  void loadProblem (  const int numcols, const int numrows,
111                     const CoinBigIndex* start, const int* index,
112                      const double* value,const int * length,
113                     const double* collb, const double* colub,   
114                     const double* obj,
115                      const double* rowlb, const double* rowub,
116                      const double * rowObjective=NULL);
117  /** Load up quadratic objective.  This is stored as a CoinPackedMatrix */
118  void loadQuadraticObjective(const int numberColumns, 
119                              const CoinBigIndex * start,
120                              const int * column, const double * element);
121  void loadQuadraticObjective (  const CoinPackedMatrix& matrix);
122  /// Get rid of quadratic objective
123  void deleteQuadraticObjective();
124  /// This just loads up a row objective
125  void setRowObjective(const double * rowObjective);
126  /// Read an mps file from the given filename
127  int readMps(const char *filename,
128              bool keepNames=false,
129              bool ignoreErrors = false);
130  /// Read GMPL files from the given filenames
131  int readGMPL(const char *filename,const char * dataName,
132               bool keepNames=false);
133  /// Copy in integer informations
134  void copyInIntegerInformation(const char * information);
135  /// Drop integer informations
136  void deleteIntegerInformation();
137  /** Set the index-th variable to be a continuous variable */
138  void setContinuous(int index);
139  /** Set the index-th variable to be an integer variable */
140  void setInteger(int index);
141  /** Return true if the index-th variable is an integer variable */
142  bool isInteger(int index) const;
143  /// Resizes rim part of model
144  void resize (int newNumberRows, int newNumberColumns);
145  /// Deletes rows
146  void deleteRows(int number, const int * which);
147  /// Add one row
148  void addRow(int numberInRow, const int * columns,
149               const double * elements, double rowLower=-COIN_DBL_MAX, 
150              double rowUpper=COIN_DBL_MAX);
151  /// Add rows
152  void addRows(int number, const double * rowLower, 
153               const double * rowUpper,
154               const CoinBigIndex * rowStarts, const int * columns,
155               const double * elements);
156  /// Add rows
157  void addRows(int number, const double * rowLower, 
158               const double * rowUpper,
159               const CoinBigIndex * rowStarts, const int * rowLengths,
160               const int * columns,
161               const double * elements);
162#ifndef CLP_NO_VECTOR
163  void addRows(int number, const double * rowLower, 
164               const double * rowUpper,
165               const CoinPackedVectorBase * const * rows);
166#endif
167  /** Add rows from a build object.
168      If tryPlusMinusOne then will try adding as +-1 matrix
169      if no matrix exists.
170      Returns number of errors e.g. duplicates
171  */
172  int addRows(const CoinBuild & buildObject,bool tryPlusMinusOne=false,
173               bool checkDuplicates=true);
174  /** Add rows from a model object.  returns
175      -1 if object in bad state (i.e. has column information)
176      otherwise number of errors.
177
178      modelObject non const as can be regularized as part of build
179      If tryPlusMinusOne then will try adding as +-1 matrix
180      if no matrix exists.
181  */
182  int addRows(CoinModel & modelObject,bool tryPlusMinusOne=false,
183              bool checkDuplicates=true);
184
185  /// Deletes columns
186  void deleteColumns(int number, const int * which);
187  /// Add one column
188  void addColumn(int numberInColumn,
189                 const int * rows,
190                 const double * elements,
191                 double columnLower=0.0, 
192                 double  columnUpper=COIN_DBL_MAX,
193                 double  objective=0.0);
194  /// Add columns
195  void addColumns(int number, const double * columnLower, 
196                  const double * columnUpper,
197                  const double * objective,
198                  const CoinBigIndex * columnStarts, const int * rows,
199                  const double * elements);
200  void addColumns(int number, const double * columnLower, 
201                  const double * columnUpper,
202                  const double * objective,
203                  const CoinBigIndex * columnStarts, const int * columnLengths,
204                  const int * rows,
205                  const double * elements);
206#ifndef CLP_NO_VECTOR
207  void addColumns(int number, const double * columnLower, 
208               const double * columnUpper,
209                  const double * objective,
210               const CoinPackedVectorBase * const * columns);
211#endif
212  /** Add columns from a build object
213      If tryPlusMinusOne then will try adding as +-1 matrix
214      if no matrix exists.
215      Returns number of errors e.g. duplicates
216  */
217  int addColumns(const CoinBuild & buildObject,bool tryPlusMinusOne=false,
218                  bool checkDuplicates=true);
219  /** Add columns from a model object.  returns
220      -1 if object in bad state (i.e. has row information)
221      otherwise number of errors
222      modelObject non const as can be regularized as part of build
223      If tryPlusMinusOne then will try adding as +-1 matrix
224      if no matrix exists.
225  */
226  int addColumns(CoinModel & modelObject,bool tryPlusMinusOne=false,
227                 bool checkDuplicates=true);
228  /// Modify one element of a matrix
229  inline void modifyCoefficient(int row, int column, double newElement,
230                           bool keepZero=false)
231        {matrix_->modifyCoefficient(row,column,newElement,keepZero);}
232  /** Change row lower bounds */
233  void chgRowLower(const double * rowLower);
234  /** Change row upper bounds */
235  void chgRowUpper(const double * rowUpper);
236  /** Change column lower bounds */
237  void chgColumnLower(const double * columnLower);
238  /** Change column upper bounds */
239  void chgColumnUpper(const double * columnUpper);
240  /** Change objective coefficients */
241  void chgObjCoefficients(const double * objIn); 
242  /** Borrow model.  This is so we don't have to copy large amounts
243      of data around.  It assumes a derived class wants to overwrite
244      an empty model with a real one - while it does an algorithm */
245  void borrowModel(ClpModel & otherModel);
246  /** Return model - nulls all arrays so can be deleted safely
247      also updates any scalars */
248  void returnModel(ClpModel & otherModel);
249
250  /// Create empty ClpPackedMatrix
251  void createEmptyMatrix();
252  /** Really clean up matrix (if ClpPackedMatrix).
253      a) eliminate all duplicate AND small elements in matrix
254      b) remove all gaps and set extraGap_ and extraMajor_ to 0.0
255      c) reallocate arrays and make max lengths equal to lengths
256      d) orders elements
257      returns number of elements eliminated or -1 if not ClpPackedMatrix
258  */
259  int cleanMatrix(double threshold=1.0e-20);
260#ifndef CLP_NO_STD
261  /// Drops names - makes lengthnames 0 and names empty
262  void dropNames();
263  /// Copies in names
264  void copyNames(std::vector<std::string> & rowNames,
265                 std::vector<std::string> & columnNames);
266  /// Copies in Row names - modifies names first .. last-1
267  void copyRowNames(const std::vector<std::string> & rowNames,int first, int last);
268  /// Copies in Column names - modifies names first .. last-1
269  void copyColumnNames(const std::vector<std::string> & columnNames, int first, int last);
270  /// Copies in Row names - modifies names first .. last-1
271  void copyRowNames(const char * const * rowNames,int first, int last);
272  /// Copies in Column names - modifies names first .. last-1
273  void copyColumnNames(const char * const * columnNames, int first, int last);
274  /// Set name of row
275  void setRowName(int rowIndex, std::string & name) ;
276  /// Set name of col
277  void setColumnName(int colIndex, std::string & name) ;
278#endif
279  /** Find a network subset.
280      rotate array should be numberRows.  On output
281      -1 not in network
282       0 in network as is
283       1 in network with signs swapped
284      Returns number of network rows
285  */
286  int findNetwork(char * rotate, double fractionNeeded=0.75);
287  /** This creates a coinModel object
288  */
289  CoinModel * createCoinModel() const;
290
291    /** Write the problem in MPS format to the specified file.
292
293        Row and column names may be null.
294        formatType is
295        <ul>
296          <li> 0 - normal
297          <li> 1 - extra accuracy
298          <li> 2 - IEEE hex (later)
299        </ul>
300
301        Returns non-zero on I/O error
302    */
303    int writeMps(const char *filename, 
304                  int formatType=0,int numberAcross=2,
305                 double objSense=0.0) const ;
306  //@}
307  /**@name gets and sets */
308  //@{
309   /// Number of rows
310   inline int numberRows() const {
311      return numberRows_;
312   }
313   inline int getNumRows() const {
314      return numberRows_;
315   }
316   /// Number of columns
317   inline int getNumCols() const {
318      return numberColumns_;
319   }
320   inline int numberColumns() const {
321      return numberColumns_;
322   }
323   /// Primal tolerance to use
324   inline double primalTolerance() const {
325      return dblParam_[ClpPrimalTolerance];
326   }
327   void setPrimalTolerance( double value) ;
328   /// Dual tolerance to use
329   inline double dualTolerance() const  { return dblParam_[ClpDualTolerance]; }
330   void setDualTolerance( double value) ;
331  /// Primal objective limit
332  inline double primalObjectiveLimit() const { return dblParam_[ClpPrimalObjectiveLimit];}
333  void setPrimalObjectiveLimit(double value);
334  /// Dual objective limit
335  inline double dualObjectiveLimit() const { return dblParam_[ClpDualObjectiveLimit];}
336  void setDualObjectiveLimit(double value);
337  /// Objective offset
338  inline double objectiveOffset() const { return dblParam_[ClpObjOffset];}
339  void setObjectiveOffset(double value);
340  /// Presolve tolerance to use
341  inline double presolveTolerance() const
342  { return dblParam_[ClpPresolveTolerance];}
343#ifndef CLP_NO_STD
344  inline std::string problemName() const { return strParam_[ClpProbName]; }
345#endif
346   /// Number of iterations
347   inline int numberIterations() const  { return numberIterations_; }
348   inline int getIterationCount() const { return numberIterations_; }
349  inline void setNumberIterations(int numberIterations)
350  { numberIterations_ = numberIterations;}
351  /** Solve type - 1 simplex, 2 simplex interface, 3 Interior.*/
352  inline int solveType() const
353  { return solveType_;}
354  inline void setSolveType(int type)
355  { solveType_=type;}
356   /// Maximum number of iterations
357   inline int maximumIterations() const { return intParam_[ClpMaxNumIteration]; }
358   void setMaximumIterations(int value);
359  /// Maximum time in seconds (from when set called)
360   inline double maximumSeconds() const { return dblParam_[ClpMaxSeconds]; }
361   void setMaximumSeconds(double value);
362  /// Returns true if hit maximum iterations (or time)
363  bool hitMaximumIterations() const;
364   /** Status of problem:
365       -1 - unknown e.g. before solve or if postSolve says not optimal
366       0 - optimal
367       1 - primal infeasible
368       2 - dual infeasible
369       3 - stopped on iterations or time
370       4 - stopped due to errors
371       5 - stopped by event handler (virtual int ClpEventHandler::event())
372   */
373   inline int status() const            { return problemStatus_; }
374   inline int problemStatus() const            { return problemStatus_; }
375  /// Set problem status
376  inline void setProblemStatus(int problemStatus)
377  { problemStatus_ = problemStatus;}
378   /** Secondary status of problem - may get extended
379       0 - none
380       1 - primal infeasible because dual limit reached OR probably primal
381       infeasible but can't prove it (main status 4)
382       2 - scaled problem optimal - unscaled problem has primal infeasibilities
383       3 - scaled problem optimal - unscaled problem has dual infeasibilities
384       4 - scaled problem optimal - unscaled problem has primal and dual infeasibilities
385       5 - giving up in primal with flagged variables
386       6 - failed due to empty problem check
387       7 - postSolve says not optimal
388       8 - failed due to bad element check
389       9 - status was 3 and stopped on time
390       100 up - translation of enum from ClpEventHandler
391   */
392   inline int secondaryStatus() const            { return secondaryStatus_; }
393  inline void setSecondaryStatus(int status)
394  { secondaryStatus_ = status;}
395   /// Are there a numerical difficulties?
396   inline bool isAbandoned() const             { return problemStatus_==4; }
397   /// Is optimality proven?
398   inline bool isProvenOptimal() const         { return problemStatus_==0; }
399   /// Is primal infeasiblity proven?
400   inline bool isProvenPrimalInfeasible() const { return problemStatus_==1; }
401   /// Is dual infeasiblity proven?
402   inline bool isProvenDualInfeasible() const  { return problemStatus_==2; }
403   /// Is the given primal objective limit reached?
404   bool isPrimalObjectiveLimitReached() const ;
405   /// Is the given dual objective limit reached?
406   bool isDualObjectiveLimitReached() const ;
407   /// Iteration limit reached?
408   inline bool isIterationLimitReached() const { return problemStatus_==3; }
409   /// Direction of optimization (1 - minimize, -1 - maximize, 0 - ignore
410   inline double optimizationDirection() const {
411      return  optimizationDirection_;
412   }
413   inline double getObjSense() const    { return optimizationDirection_; }
414   void setOptimizationDirection(double value);
415   /// Primal row solution
416   inline double * primalRowSolution() const    { return rowActivity_; }
417   inline const double * getRowActivity() const { return rowActivity_; }
418   /// Primal column solution
419   inline double * primalColumnSolution() const { return columnActivity_; }
420   inline const double * getColSolution() const { return columnActivity_; }
421   inline void setColSolution(const double * input)
422   { memcpy(columnActivity_,input,numberColumns_*sizeof(double));}
423   /// Dual row solution
424   inline double * dualRowSolution() const      { return dual_; }
425   inline const double * getRowPrice() const    { return dual_; }
426   /// Reduced costs
427   inline double * dualColumnSolution() const   { return reducedCost_; }
428   inline const double * getReducedCost() const { return reducedCost_; }
429   /// Row lower
430   inline double* rowLower() const              { return rowLower_; }
431   inline const double* getRowLower() const     { return rowLower_; }
432   /// Row upper
433   inline double* rowUpper() const              { return rowUpper_; }
434   inline const double* getRowUpper() const     { return rowUpper_; }
435    //-------------------------------------------------------------------------
436    /**@name Changing bounds on variables and constraints */
437    //@{
438       /** Set an objective function coefficient */
439       void setObjectiveCoefficient( int elementIndex, double elementValue );
440       /** Set an objective function coefficient */
441       inline void setObjCoeff( int elementIndex, double elementValue )
442       { setObjectiveCoefficient( elementIndex, elementValue);}
443
444      /** Set a single column lower bound<br>
445          Use -DBL_MAX for -infinity. */
446       void setColumnLower( int elementIndex, double elementValue );
447     
448      /** Set a single column upper bound<br>
449          Use DBL_MAX for infinity. */
450       void setColumnUpper( int elementIndex, double elementValue );
451
452      /** Set a single column lower and upper bound */
453      void setColumnBounds( int elementIndex,
454        double lower, double upper );
455
456      /** Set the bounds on a number of columns simultaneously<br>
457          The default implementation just invokes setColLower() and
458          setColUpper() over and over again.
459          @param indexFirst,indexLast pointers to the beginning and after the
460                 end of the array of the indices of the variables whose
461                 <em>either</em> bound changes
462          @param boundList the new lower/upper bound pairs for the variables
463      */
464      void setColumnSetBounds(const int* indexFirst,
465                                   const int* indexLast,
466                                   const double* boundList);
467     
468      /** Set a single column lower bound<br>
469          Use -DBL_MAX for -infinity. */
470       inline void setColLower( int elementIndex, double elementValue )
471       { setColumnLower(elementIndex, elementValue);}
472      /** Set a single column upper bound<br>
473          Use DBL_MAX for infinity. */
474       inline void setColUpper( int elementIndex, double elementValue )
475       { setColumnUpper(elementIndex, elementValue);}
476
477      /** Set a single column lower and upper bound */
478      inline void setColBounds( int elementIndex,
479        double lower, double upper )
480       { setColumnBounds(elementIndex, lower, upper);}
481
482      /** Set the bounds on a number of columns simultaneously<br>
483          @param indexFirst,indexLast pointers to the beginning and after the
484                 end of the array of the indices of the variables whose
485                 <em>either</em> bound changes
486          @param boundList the new lower/upper bound pairs for the variables
487      */
488      inline void setColSetBounds(const int* indexFirst,
489                                   const int* indexLast,
490                                   const double* boundList)
491      { setColumnSetBounds(indexFirst, indexLast, boundList);}
492     
493      /** Set a single row lower bound<br>
494          Use -DBL_MAX for -infinity. */
495      void setRowLower( int elementIndex, double elementValue );
496     
497      /** Set a single row upper bound<br>
498          Use DBL_MAX for infinity. */
499      void setRowUpper( int elementIndex, double elementValue ) ;
500   
501      /** Set a single row lower and upper bound */
502      void setRowBounds( int elementIndex,
503                                 double lower, double upper ) ;
504   
505      /** Set the bounds on a number of rows simultaneously<br>
506          @param indexFirst,indexLast pointers to the beginning and after the
507                 end of the array of the indices of the constraints whose
508                 <em>either</em> bound changes
509          @param boundList the new lower/upper bound pairs for the constraints
510      */
511      void setRowSetBounds(const int* indexFirst,
512                                   const int* indexLast,
513                                   const double* boundList);
514   
515    //@}
516   /// Scaling
517   inline const double * rowScale() const {return rowScale_;}
518   inline const double * columnScale() const {return columnScale_;}
519   inline void setRowScale(double * scale) { delete [] (double *) rowScale_; rowScale_ = scale;}
520   inline void setColumnScale(double * scale) { delete [] (double *) columnScale_; columnScale_ = scale;}
521  /// Scaling of objective
522  inline double objectiveScale() const 
523          { return objectiveScale_;} 
524  inline void setObjectiveScale(double value)
525          { objectiveScale_ = value;} 
526  /// Scaling of rhs and bounds
527  inline double rhsScale() const 
528          { return rhsScale_;} 
529  inline void setRhsScale(double value)
530          { rhsScale_ = value;} 
531   /// Sets or unsets scaling, 0 -off, 1 equilibrium, 2 geometric, 3 auto, 4 auto-but-as-initialSolve-in-bab
532   void scaling(int mode=1);
533  /** If we constructed a "really" scaled model then this reverses the operation.
534      Quantities may not be exactly as they were before due to rounding errors */
535  void unscale();
536   /// Gets scalingFlag
537   inline int scalingFlag() const {return scalingFlag_;}
538   /// Objective
539   inline double * objective() const           
540  {
541    if (objective_) {
542      double offset; 
543      return objective_->gradient(NULL,NULL,offset,false);
544    } else {
545      return NULL;
546    }
547  }
548   inline double * objective(const double * solution, double & offset,bool refresh=true) const           
549  {
550    offset=0.0;
551    if (objective_) {
552      return objective_->gradient(NULL,solution,offset,refresh);
553    } else {
554      return NULL;
555    }
556  }
557   inline const double * getObjCoefficients() const 
558  { 
559    if (objective_) {
560      double offset; 
561      return objective_->gradient(NULL,NULL,offset,false);
562    } else {
563      return NULL;
564    }
565  }
566   /// Row Objective
567   inline double * rowObjective() const         { return rowObjective_; }
568   inline const double * getRowObjCoefficients() const {
569      return rowObjective_;
570   }
571   /// Column Lower
572   inline double * columnLower() const          { return columnLower_; }
573   inline const double * getColLower() const    { return columnLower_; }
574   /// Column Upper
575   inline double * columnUpper() const          { return columnUpper_; }
576   inline const double * getColUpper() const    { return columnUpper_; }
577   /// Matrix (if not ClpPackedmatrix be careful about memory leak
578   inline CoinPackedMatrix * matrix() const {
579     if ( matrix_ == NULL ) return NULL;
580     else return matrix_->getPackedMatrix();
581   }
582   /// Number of elements in matrix
583   inline int getNumElements() const 
584     { return matrix_->getNumElements();}
585   /** Small element value - elements less than this set to zero,
586      default is 1.0e-20 */
587   inline double getSmallElementValue() const
588  { return smallElement_;}
589  inline void setSmallElementValue(double value)
590  { smallElement_=value;} 
591   /// Row Matrix
592   inline ClpMatrixBase * rowCopy() const       { return rowCopy_; }
593   /// Clp Matrix
594   inline ClpMatrixBase * clpMatrix() const     { return matrix_; }
595  /** Replace Clp Matrix (current is not deleted unless told to
596      and new is used)
597      So up to user to delete current.  This was used where
598      matrices were being rotated. ClpModel takes ownership.
599  */
600   void replaceMatrix(ClpMatrixBase * matrix,bool deleteCurrent=false);
601  /** Replace Clp Matrix (current is not deleted unless told to
602      and new is used) So up to user to delete current.  This was used where
603      matrices were being rotated.  This version changes CoinPackedMatrix
604      to ClpPackedMatrix.  ClpModel takes ownership.
605  */
606   inline void replaceMatrix(CoinPackedMatrix * matrix,
607                             bool deleteCurrent=false)
608  { replaceMatrix(new ClpPackedMatrix(matrix),deleteCurrent);}
609   /// Objective value
610   inline double objectiveValue() const {
611      return objectiveValue_*optimizationDirection_ - dblParam_[ClpObjOffset];
612   }
613  inline void setObjectiveValue(double value) {
614    objectiveValue_ = (value+ dblParam_[ClpObjOffset])/optimizationDirection_;
615   }
616   inline double getObjValue() const {
617      return objectiveValue_*optimizationDirection_ - dblParam_[ClpObjOffset];
618   }
619   /// Integer information
620   inline char * integerInformation() const     { return integerType_; }
621   /** Infeasibility/unbounded ray (NULL returned if none/wrong)
622       Up to user to use delete [] on these arrays.  */
623   double * infeasibilityRay() const;
624   double * unboundedRay() const;
625  /// See if status (i.e. basis) array exists (partly for OsiClp)
626  inline bool statusExists() const
627  { return (status_!=NULL);}
628  /// Return address of status (i.e. basis) array (char[numberRows+numberColumns])
629  inline unsigned char *  statusArray() const
630  { return status_;}
631  /** Return copy of status (i.e. basis) array (char[numberRows+numberColumns]),
632      use delete [] */
633  unsigned char *  statusCopy() const;
634  /// Copy in status (basis) vector
635  void copyinStatus(const unsigned char * statusArray);
636
637  /// User pointer for whatever reason
638  inline void setUserPointer (void * pointer)
639  { userPointer_=pointer;}
640  inline void * getUserPointer () const
641  { return userPointer_;}
642  /// What has changed in model (only for masochistic users)
643  inline int whatsChanged() const 
644          { return whatsChanged_;} 
645  inline void setWhatsChanged(int value)
646          { whatsChanged_ = value;} 
647  /// Number of threads (not really being used)
648  inline int numberThreads() const 
649          { return numberThreads_;} 
650  inline void setNumberThreads(int value)
651          { numberThreads_ = value;} 
652  //@}
653  /**@name Message handling */
654  //@{
655   /// Pass in Message handler (not deleted at end)
656   void passInMessageHandler(CoinMessageHandler * handler);
657  /// Pass in Message handler (not deleted at end) and return current
658  CoinMessageHandler * pushMessageHandler(CoinMessageHandler * handler,
659                                          bool & oldDefault);
660  /// back to previous message handler
661  void popMessageHandler(CoinMessageHandler * oldHandler,bool oldDefault);
662   /// Set language
663   void newLanguage(CoinMessages::Language language);
664   inline void setLanguage(CoinMessages::Language language) { newLanguage(language); }
665   /// Return handler
666   inline CoinMessageHandler * messageHandler() const       { return handler_; }
667   /// Return messages
668   inline CoinMessages messages() const                     { return messages_; }
669   /// Return pointer to messages
670   inline CoinMessages * messagesPointer()                  { return & messages_; }
671   /// Return Coin messages
672   inline CoinMessages coinMessages() const                  { return coinMessages_; }
673   /// Return pointer to Coin messages
674   inline CoinMessages * coinMessagesPointer()                  { return & coinMessages_; }
675  /** Amount of print out:
676      0 - none
677      1 - just final
678      2 - just factorizations
679      3 - as 2 plus a bit more
680      4 - verbose
681      above that 8,16,32 etc just for selective debug
682  */
683   inline void setLogLevel(int value)    { handler_->setLogLevel(value); }
684   inline int logLevel() const           { return handler_->logLevel(); }
685   /// Return true if default handler
686   inline bool defaultHandler() const
687   { return defaultHandler_;}
688   /// Pass in Event handler (cloned and deleted at end)
689   void passInEventHandler(const ClpEventHandler * eventHandler);
690   /// Event handler
691   inline ClpEventHandler * eventHandler() const
692  { return eventHandler_;}
693  /// Thread specific random number generator
694  inline CoinThreadRandom * randomNumberGenerator() 
695  { return &randomNumberGenerator_;}
696  /// Thread specific random number generator
697  inline CoinThreadRandom & mutableRandomNumberGenerator()
698  { return randomNumberGenerator_;}
699  /// Set seed for thread specific random number generator
700  inline void setRandomSeed(int value)
701  { randomNumberGenerator_.setSeed(value);}
702   /// length of names (0 means no names0
703   inline int lengthNames() const { return lengthNames_; }
704#ifndef CLP_NO_STD
705   /// length of names (0 means no names0
706   inline void setLengthNames(int value) { lengthNames_=value; }
707   /// Row names
708   inline const std::vector<std::string> * rowNames() const {
709      return &rowNames_;
710   }
711   inline const std::string& rowName(int iRow) const {
712      return rowNames_[iRow];
713   }
714   /// Return name or Rnnnnnnn
715   std::string getRowName(int iRow) const;
716   /// Column names
717   inline const std::vector<std::string> * columnNames() const {
718      return &columnNames_;
719   }
720   inline const std::string& columnName(int iColumn) const {
721      return columnNames_[iColumn];
722   }
723   /// Return name or Cnnnnnnn
724   std::string getColumnName(int iColumn) const;
725#endif
726  /// Objective methods
727  inline ClpObjective * objectiveAsObject() const
728  { return objective_;}
729  void setObjective(ClpObjective * objective);
730  inline void setObjectivePointer(ClpObjective * objective)
731  { objective_ = objective;}
732  /** Solve a problem with no elements - return status and
733      dual and primal infeasibilites */
734  int emptyProblem(int * infeasNumber=NULL, double * infeasSum=NULL,bool printMessage=true);
735 
736  //@}
737
738  /**@name Matrix times vector methods
739     They can be faster if scalar is +- 1
740     These are covers so user need not worry about scaling
741     Also for simplex I am not using basic/non-basic split */
742  //@{
743    /** Return <code>y + A * x * scalar</code> in <code>y</code>.
744        @pre <code>x</code> must be of size <code>numColumns()</code>
745        @pre <code>y</code> must be of size <code>numRows()</code> */
746   void times(double scalar,
747                       const double * x, double * y) const;
748    /** Return <code>y + x * scalar * A</code> in <code>y</code>.
749        @pre <code>x</code> must be of size <code>numRows()</code>
750        @pre <code>y</code> must be of size <code>numColumns()</code> */
751    void transposeTimes(double scalar,
752                                const double * x, double * y) const ;
753  //@}
754
755
756  //---------------------------------------------------------------------------
757  /**@name Parameter set/get methods
758
759     The set methods return true if the parameter was set to the given value,
760     false otherwise. There can be various reasons for failure: the given
761     parameter is not applicable for the solver (e.g., refactorization
762     frequency for the volume algorithm), the parameter is not yet implemented
763     for the solver or simply the value of the parameter is out of the range
764     the solver accepts. If a parameter setting call returns false check the
765     details of your solver.
766
767     The get methods return true if the given parameter is applicable for the
768     solver and is implemented. In this case the value of the parameter is
769     returned in the second argument. Otherwise they return false.
770
771     ** once it has been decided where solver sits this may be redone
772  */
773  //@{
774    /// Set an integer parameter
775    bool setIntParam(ClpIntParam key, int value) ;
776    /// Set an double parameter
777    bool setDblParam(ClpDblParam key, double value) ;
778#ifndef CLP_NO_STD
779    /// Set an string parameter
780    bool setStrParam(ClpStrParam key, const std::string & value);
781#endif
782    // Get an integer parameter
783    inline bool getIntParam(ClpIntParam key, int& value) const {
784      if (key<ClpLastIntParam) {
785        value = intParam_[key];
786        return true;
787      } else {
788        return false;
789      }
790    }
791    // Get an double parameter
792    inline bool getDblParam(ClpDblParam key, double& value) const {
793      if (key<ClpLastDblParam) {
794        value = dblParam_[key];
795        return true;
796      } else {
797        return false;
798      }
799    }
800#ifndef CLP_NO_STD
801    // Get a string parameter
802    inline bool getStrParam(ClpStrParam key, std::string& value) const {
803      if (key<ClpLastStrParam) {
804        value = strParam_[key];
805        return true;
806      } else {
807        return false;
808      }
809    }
810#endif
811    /// Create C++ lines to get to current state
812    void generateCpp( FILE * fp);
813  /** For advanced options
814      1 - Don't keep changing infeasibility weight
815      2 - Keep nonLinearCost round solves
816      4 - Force outgoing variables to exact bound (primal)
817      8 - Safe to use dense initial factorization
818      16 -Just use basic variables for operation if column generation
819      32 -Clean up with primal before strong branching
820      64 -Treat problem as feasible until last minute (i.e. minimize infeasibilities)
821      128 - Switch off all matrix sanity checks
822      256 - No row copy
823      512 - If not in values pass, solution guaranteed, skip as much as possible
824      1024 - In branch and bound
825      2048 - Don't bother to re-factorize if < 20 iterations
826      4096 - Skip some optimality checks
827      8192 - Do Primal when cleaning up primal
828      16384 - In fast dual (so we can switch off things)
829      32678 - called from Osi
830      65356 - keep arrays around as much as possible
831      131072 - scale factor arrays have inverse values at end
832      NOTE - many applications can call Clp but there may be some short cuts
833             which are taken which are not guaranteed safe from all applications.
834             Vetted applications will have a bit set and the code may test this
835             At present I expect a few such applications - if too many I will
836             have to re-think.  It is up to application owner to change the code
837             if she/he needs these short cuts.  I will not debug unless in Coin
838             repository.  See COIN_CLP_VETTED comments.
839      0x01000000 is Cbc (and in branch and bound)
840      0x02000000 is in a different branch and bound
841  */
842#define COIN_CBC_USING_CLP 0x01000000
843  inline unsigned int specialOptions() const
844  { return specialOptions_;}
845  void setSpecialOptions(unsigned int value);
846  //@}
847
848  /**@name private or protected methods */
849  //@{
850protected:
851  /// Does most of deletion
852  void gutsOfDelete();
853  /** Does most of copying
854      If trueCopy false then just points to arrays */
855  void gutsOfCopy(const ClpModel & rhs, bool trueCopy=true);
856  /// gets lower and upper bounds on rows
857  void getRowBound(int iRow, double& lower, double& upper) const;
858  /// puts in format I like - 4 array matrix - may make row copy
859  void gutsOfLoadModel ( int numberRows, int numberColumns,
860                     const double* collb, const double* colub,   
861                     const double* obj,
862                     const double* rowlb, const double* rowub,
863                      const double * rowObjective=NULL);
864  /// Does much of scaling
865  void gutsOfScaling();
866   /// Objective value - always minimize
867   inline double rawObjectiveValue() const {
868      return objectiveValue_;
869   }
870  /// Create row names as char **
871  const char * const * rowNamesAsChar() const;
872  /// Create column names as char **
873  const char * const * columnNamesAsChar() const;
874  /// Delete char * version of names
875  void deleteNamesAsChar(const char * const * names,int number) const;
876  /// On stopped - sets secondary status
877  void onStopped();
878  //@}
879
880
881////////////////// data //////////////////
882protected:
883
884  /**@name data */
885  //@{
886  /// Direction of optimization (1 - minimize, -1 - maximize, 0 - ignore
887  double optimizationDirection_;
888  /// Array of double parameters
889  double dblParam_[ClpLastDblParam];
890  /// Objective value
891  double objectiveValue_;
892  /// Small element value
893  double smallElement_;
894  /// Scaling of objective
895  double objectiveScale_;
896  /// Scaling of rhs and bounds
897  double rhsScale_;
898  /// Number of rows
899  int numberRows_;
900  /// Number of columns
901  int numberColumns_;
902  /// Row activities
903  double * rowActivity_;
904  /// Column activities
905  double * columnActivity_;
906  /// Duals
907  double * dual_;
908  /// Reduced costs
909  double * reducedCost_;
910  /// Row lower
911  double* rowLower_;
912  /// Row upper
913  double* rowUpper_;
914  /// Objective
915  ClpObjective * objective_;
916  /// Row Objective (? sign)  - may be NULL
917  double * rowObjective_;
918  /// Column Lower
919  double * columnLower_;
920  /// Column Upper
921  double * columnUpper_;
922  /// Packed matrix
923  ClpMatrixBase * matrix_;
924  /// Row copy if wanted
925  ClpMatrixBase * rowCopy_;
926  /// Infeasible/unbounded ray
927  double * ray_;
928  /// Row scale factors for matrix
929  double * rowScale_;
930  /// Column scale factors
931  double * columnScale_;
932  /// Scale flag, 0 none, 1 equilibrium, 2 geometric, 3, auto, 4 dynamic
933  int scalingFlag_;
934  /** Status (i.e. basis) Region.  I know that not all algorithms need a status
935      array, but it made sense for things like crossover and put
936      all permanent stuff in one place.  No assumption is made
937      about what is in status array (although it might be good to reserve
938      bottom 3 bits (i.e. 0-7 numeric) for classic status).  This
939      is number of columns + number of rows long (in that order).
940  */
941  unsigned char * status_;
942  /// Integer information
943  char * integerType_;
944  /// User pointer for whatever reason
945  void * userPointer_;
946  /// Array of integer parameters
947  int intParam_[ClpLastIntParam];
948  /// Number of iterations
949  int numberIterations_;
950  /** Solve type - 1 simplex, 2 simplex interface, 3 Interior.*/
951  int solveType_;
952  /** Whats changed since last solve.  This is a work in progress
953      It is designed so careful people can make go faster.
954      It is only used when startFinishOptions used in dual or primal.
955      Bit 1 - number of rows/columns has not changed (so work arrays valid)
956          2 - matrix has not changed
957          4 - if matrix has changed only by adding rows
958          8 - if matrix has changed only by adding columns
959         16 - row lbs not changed
960         32 - row ubs not changed
961         64 - column objective not changed
962        128 - column lbs not changed
963        256 - column ubs not changed
964        512 - basis not changed (up to user to set this to 0)
965              top bits may be used internally
966  */
967  unsigned int whatsChanged_;
968  /// Status of problem
969  int problemStatus_;
970  /// Secondary status of problem
971  int secondaryStatus_;
972  /// length of names (0 means no names)
973  int lengthNames_;
974  /// Number of threads (not very operational)
975  int numberThreads_;
976  /** For advanced options
977      See get and set for meaning
978  */
979  unsigned int specialOptions_;
980  /// Message handler
981  CoinMessageHandler * handler_;
982  /// Flag to say if default handler (so delete)
983  bool defaultHandler_;
984  /// Thread specific random number generator
985  CoinThreadRandom randomNumberGenerator_;
986  /// Event handler
987  ClpEventHandler * eventHandler_;
988#ifndef CLP_NO_STD
989  /// Row names
990  std::vector<std::string> rowNames_;
991  /// Column names
992  std::vector<std::string> columnNames_;
993#endif
994  /// Messages
995  CoinMessages messages_;
996  /// Coin messages
997  CoinMessages coinMessages_;
998#ifndef CLP_NO_STD
999  /// Array of string parameters
1000  std::string strParam_[ClpLastStrParam];
1001#endif
1002  //@}
1003};
1004/** This is a tiny class where data can be saved round calls.
1005 */
1006class ClpDataSave {
1007
1008public:
1009  /**@name Constructors and destructor
1010   */
1011  //@{
1012    /// Default constructor
1013    ClpDataSave (  );
1014
1015    /// Copy constructor.
1016    ClpDataSave(const ClpDataSave &);
1017    /// Assignment operator. This copies the data
1018    ClpDataSave & operator=(const ClpDataSave & rhs);
1019    /// Destructor
1020    ~ClpDataSave (  );
1021
1022  //@}
1023
1024////////////////// data //////////////////
1025public:
1026
1027  /**@name data - with same names as in other classes*/
1028  //@{
1029  double dualBound_;
1030  double infeasibilityCost_;
1031  double pivotTolerance_;
1032  double acceptablePivot_;
1033  double objectiveScale_;
1034  int sparseThreshold_;
1035  int perturbation_;
1036  int forceFactorization_;
1037  int scalingFlag_;
1038  //@}
1039};
1040
1041#endif
Note: See TracBrowser for help on using the repository browser.