lemon/lp_base.h
changeset 2303 005b3f927287
parent 2268 ad15bdd334bf
child 2309 468a525d5b45
equal deleted inserted replaced
36:101036c2a324 37:8c74ecd9886a
    37     
    37     
    38   ///\todo This might be implemented to be also usable in other places.
    38   ///\todo This might be implemented to be also usable in other places.
    39   class _FixId 
    39   class _FixId 
    40   {
    40   {
    41   protected:
    41   protected:
       
    42     int _first_index;
       
    43     int first_free;
       
    44   public:
    42     std::vector<int> index;
    45     std::vector<int> index;
    43     std::vector<int> cross;
    46     std::vector<int> cross;
    44     int first_free;
    47     _FixId() : _first_index(-1), first_free(-1) {};
    45   public:
       
    46     _FixId() : first_free(-1) {};
       
    47     ///Convert a floating id to a fix one
    48     ///Convert a floating id to a fix one
    48 
    49 
    49     ///\param n is a floating id
    50     ///\param n is a floating id
    50     ///\return the corresponding fix id
    51     ///\return the corresponding fix id
    51     int fixId(int n) const {return cross[n];}
    52     int fixId(int n) const {return cross[n];}
    59     ///\param n is a floating id
    60     ///\param n is a floating id
    60     ///\return the fix id of the new value
    61     ///\return the fix id of the new value
    61     ///\todo Multiple additions should also be handled.
    62     ///\todo Multiple additions should also be handled.
    62     int insert(int n)
    63     int insert(int n)
    63     {
    64     {
       
    65       if(cross.empty()) _first_index=n;
    64       if(n>=int(cross.size())) {
    66       if(n>=int(cross.size())) {
    65 	cross.resize(n+1);
    67 	cross.resize(n+1);
    66 	if(first_free==-1) {
    68 	if(first_free==-1) {
    67 	  cross[n]=index.size();
    69 	  cross[n]=index.size();
    68 	  index.push_back(n);
    70 	  index.push_back(n);
    99 
   101 
   100     ///\todo Do we need this?
   102     ///\todo Do we need this?
   101     ///
   103     ///
   102     std::size_t maxFixId() { return cross.size()-1; }
   104     std::size_t maxFixId() { return cross.size()-1; }
   103   
   105   
       
   106     ///Returns the first (smallest) inserted index
       
   107 
       
   108     ///Returns the first (smallest) inserted index
       
   109     ///or -1 if no index has been inserted before.
       
   110     int firstIndex() {return _first_index;}
   104   };
   111   };
   105     
   112     
   106   ///Common base class for LP solvers
   113   ///Common base class for LP solvers
   107   
   114   
   108   ///\todo Much more docs
   115   ///\todo Much more docs
   109   ///\ingroup gen_opt_group
   116   ///\ingroup gen_opt_group
   110   class LpSolverBase {
   117   class LpSolverBase {
       
   118 
       
   119   protected:
       
   120     _FixId rows;
       
   121     _FixId cols;
   111 
   122 
   112   public:
   123   public:
   113 
   124 
   114     ///Possible outcomes of an LP solving procedure
   125     ///Possible outcomes of an LP solving procedure
   115     enum SolveExitStatus {
   126     enum SolveExitStatus {
   161     static const Value INF;
   172     static const Value INF;
   162     ///The not a number constant
   173     ///The not a number constant
   163     static const Value NaN;
   174     static const Value NaN;
   164 
   175 
   165     static inline bool isNaN(const Value& v) { return v!=v; }
   176     static inline bool isNaN(const Value& v) { return v!=v; }
       
   177     
       
   178     friend class Col;
       
   179     friend class ColIt;
       
   180     friend class Row;
   166     
   181     
   167     ///Refer to a column of the LP.
   182     ///Refer to a column of the LP.
   168 
   183 
   169     ///This type is used to refer to a column of the LP.
   184     ///This type is used to refer to a column of the LP.
   170     ///
   185     ///
   187       bool operator> (Col c) const  {return id> c.id;}
   202       bool operator> (Col c) const  {return id> c.id;}
   188       bool operator==(Col c) const  {return id==c.id;}
   203       bool operator==(Col c) const  {return id==c.id;}
   189       bool operator!=(Col c) const  {return id!=c.id;}
   204       bool operator!=(Col c) const  {return id!=c.id;}
   190     };
   205     };
   191 
   206 
       
   207     class ColIt : public Col {
       
   208       LpSolverBase *_lp;
       
   209       ColIt() {}
       
   210       ColIt(LpSolverBase &lp) : _lp(&lp)
       
   211       {
       
   212 	id = _lp->cols.cross.empty()?-1:
       
   213 	  _lp->cols.fixId(_lp->cols.firstIndex());
       
   214       }
       
   215       ColIt(const Invalid&) : Col(INVALID) {}
       
   216       ColIt &operator++() 
       
   217       {
       
   218 	int fid = _lp->cols.floatingId(id)+1;
       
   219 	id = unsigned(fid)<_lp->cols.cross.size() ? _lp->cols.fixId(fid) : -1;
       
   220 	return *this;
       
   221       }
       
   222     };
       
   223       
   192     ///Refer to a row of the LP.
   224     ///Refer to a row of the LP.
   193 
   225 
   194     ///This type is used to refer to a row of the LP.
   226     ///This type is used to refer to a row of the LP.
   195     ///
   227     ///
   196     ///Its value remains valid and correct even after the addition or erase of
   228     ///Its value remains valid and correct even after the addition or erase of
   562       }
   594       }
   563     };
   595     };
   564     
   596     
   565 
   597 
   566   protected:
   598   protected:
   567     _FixId rows;
       
   568     _FixId cols;
       
   569 
   599 
   570     //Abstract virtual functions
   600     //Abstract virtual functions
   571     virtual LpSolverBase &_newLp() = 0;
   601     virtual LpSolverBase &_newLp() = 0;
   572     virtual LpSolverBase &_copyLp(){
   602     virtual LpSolverBase &_copyLp(){
   573       ///\todo This should be implemented here, too,  when we have problem retrieving routines. It can be overriden.
   603       ///\todo This should be implemented here, too,  when we have problem retrieving routines. It can be overriden.
   577       return newlp;
   607       return newlp;
   578       //return *(LpSolverBase*)0;
   608       //return *(LpSolverBase*)0;
   579     };
   609     };
   580 
   610 
   581     virtual int _addCol() = 0;
   611     virtual int _addCol() = 0;
   582     virtual int _addRow() = 0;
   612     virtual int _addRow() = 0; 
   583     virtual void _eraseCol(int col) = 0;
   613     virtual void _eraseCol(int col) = 0;
   584     virtual void _eraseRow(int row) = 0;
   614     virtual void _eraseRow(int row) = 0;
   585     virtual void _getColName(int col,       std::string & name) = 0;
   615     virtual void _getColName(int col,       std::string & name) = 0;
   586     virtual void _setColName(int col, const std::string & name) = 0;
   616     virtual void _setColName(int col, const std::string & name) = 0;
   587     virtual void _setRowCoeffs(int i, 
   617     virtual void _setRowCoeffs(int i,