00001
00002
00003 #ifndef CoinPackedMatrix_H
00004 #define CoinPackedMatrix_H
00005
00006 #include "CoinError.hpp"
00007 #ifndef CLP_NO_VECTOR
00008 #include "CoinPackedVectorBase.hpp"
00009 #include "CoinShallowPackedVector.hpp"
00010 #else
00011 #include "CoinFinite.hpp"
00012 #include "CoinFloatEqual.hpp"
00013 #endif
00014
00061 class CoinPackedMatrix {
00062 friend void CoinPackedMatrixUnitTest();
00063
00064 public:
00065
00066
00067
00071 double getExtraGap() const { return extraGap_; }
00073 double getExtraMajor() const { return extraMajor_; }
00074
00077 void reserve(const int newMaxMajorDim, const CoinBigIndex newMaxSize,
00078 bool create=false);
00080 void clear();
00081
00083 bool isColOrdered() const { return colOrdered_; }
00085 CoinBigIndex getNumElements() const { return size_; }
00087 int getNumCols() const { return colOrdered_ ? majorDim_ : minorDim_; }
00089 int getNumRows() const { return colOrdered_ ? minorDim_ : majorDim_; }
00090
00095 inline const double * getElements() const { return element_; }
00101 inline const int * getIndices() const { return index_; }
00102
00104 int getSizeVectorStarts()const { return majorDim_ > 0 ? majorDim_+1 : 0;}
00106 int getSizeVectorLengths() const { return majorDim_; }
00109 inline const CoinBigIndex * getVectorStarts() const { return start_; }
00111 inline const int * getVectorLengths() const { return length_; }
00112
00113
00116 CoinBigIndex getVectorFirst(const int i) const {
00117 if (i < 0 || i >= majorDim_)
00118 throw CoinError("bad index", "vectorFirst", "CoinPackedMatrix");
00119 return start_[i];
00120 }
00123 CoinBigIndex getVectorLast(const int i) const {
00124 if (i < 0 || i >= majorDim_)
00125 throw CoinError("bad index", "vectorLast", "CoinPackedMatrix");
00126 return start_[i] + length_[i];
00127 }
00129 inline int getVectorSize(const int i) const {
00130 if (i < 0 || i >= majorDim_)
00131 throw CoinError("bad index", "vectorSize", "CoinPackedMatrix");
00132 return length_[i];
00133 }
00134 #ifndef CLP_NO_VECTOR
00135
00136 const CoinShallowPackedVector getVector(int i) const {
00137 if (i < 0 || i >= majorDim_)
00138 throw CoinError("bad index", "vector", "CoinPackedMatrix");
00139 return CoinShallowPackedVector(length_[i],
00140 index_ + start_[i],
00141 element_ + start_[i],
00142 false);
00143 }
00144 #endif
00145
00155 int * getMajorIndices() const;
00157
00158
00166 void setDimensions(int numrows, int numcols);
00167
00169 void setExtraGap(const double newGap);
00171 void setExtraMajor(const double newMajor);
00172 #ifndef CLP_NO_VECTOR
00173
00177 void appendCol(const CoinPackedVectorBase& vec);
00178 #endif
00179
00183 void appendCol(const int vecsize,
00184 const int *vecind, const double *vecelem);
00185 #ifndef CLP_NO_VECTOR
00186
00191 void appendCols(const int numcols,
00192 const CoinPackedVectorBase * const * cols);
00193 #endif
00194
00197 int appendCols(const int numcols,
00198 const CoinBigIndex * columnStarts, const int * row,
00199 const double * element, int numberRows=-1);
00200 #ifndef CLP_NO_VECTOR
00201
00205 void appendRow(const CoinPackedVectorBase& vec);
00206 #endif
00207
00211 void appendRow(const int vecsize,
00212 const int *vecind, const double *vecelem);
00213 #ifndef CLP_NO_VECTOR
00214
00219 void appendRows(const int numrows,
00220 const CoinPackedVectorBase * const * rows);
00221 #endif
00222
00225 int appendRows(const int numrows,
00226 const CoinBigIndex * rowStarts, const int * column,
00227 const double * element, int numberColumns=-1);
00228
00233 void rightAppendPackedMatrix(const CoinPackedMatrix& matrix);
00238 void bottomAppendPackedMatrix(const CoinPackedMatrix& matrix);
00239
00241 void deleteCols(const int numDel, const int * indDel);
00243 void deleteRows(const int numDel, const int * indDel);
00244
00248 void replaceVector(const int index,
00249 const int numReplace, const double * newElements);
00254 void modifyCoefficient(int row, int column, double newElement,
00255 bool keepZero=false);
00259 double getCoefficient(int row, int column) const;
00260
00266 int compress(double threshold);
00271 int eliminateDuplicates(double threshold);
00273 void orderMatrix();
00281 int cleanMatrix(double threshold=1.0e-20);
00283
00284
00289 void removeGaps(double removeValue=-1.0);
00290
00294 void submatrixOf(const CoinPackedMatrix& matrix,
00295 const int numMajor, const int * indMajor);
00299 void submatrixOfWithDuplicates(const CoinPackedMatrix& matrix,
00300 const int numMajor, const int * indMajor);
00301 #if 0
00302
00305 void submatrixOf(const CoinPackedMatrix& matrix,
00306 const int numMajor, const int * indMajor,
00307 const int numMinor, const int * indMinor);
00308 #endif
00309
00312 void copyOf(const CoinPackedMatrix& rhs);
00316 void copyOf(const bool colordered,
00317 const int minor, const int major, const CoinBigIndex numels,
00318 const double * elem, const int * ind,
00319 const CoinBigIndex * start, const int * len,
00320 const double extraMajor=0.0, const double extraGap=0.0);
00324 void reverseOrderedCopyOf(const CoinPackedMatrix& rhs);
00333 void assignMatrix(const bool colordered,
00334 const int minor, const int major,
00335 const CoinBigIndex numels,
00336 double *& elem, int *& ind,
00337 CoinBigIndex *& start, int *& len,
00338 const int maxmajor = -1, const CoinBigIndex maxsize = -1);
00339
00340
00341
00344 CoinPackedMatrix & operator=(const CoinPackedMatrix& rhs);
00345
00347 void reverseOrdering();
00354 void transpose();
00355
00357 void swap(CoinPackedMatrix& matrix);
00358
00360
00361
00367 void times(const double * x, double * y) const;
00368 #ifndef CLP_NO_VECTOR
00369
00371 void times(const CoinPackedVectorBase& x, double * y) const;
00372 #endif
00373
00376 void transposeTimes(const double * x, double * y) const;
00377 #ifndef CLP_NO_VECTOR
00378
00380 void transposeTimes(const CoinPackedVectorBase& x, double * y) const;
00381 #endif
00382
00383
00384
00392
00393
00400 int * countOrthoLength() const;
00403 int getMajorDim() const { return majorDim_; }
00406 int getMinorDim() const { return minorDim_; }
00410 int getMaxMajorDim() const { return maxMajorDim_; }
00411
00414 void dumpMatrix(const char* fname = NULL) const;
00415
00417 void printMatrixElement(const int row_val, const int col_val) const;
00419
00420
00427 #ifndef CLP_NO_VECTOR
00428
00429 void appendMajorVector(const CoinPackedVectorBase& vec);
00430 #endif
00431
00432 void appendMajorVector(const int vecsize, const int *vecind,
00433 const double *vecelem);
00434 #ifndef CLP_NO_VECTOR
00435
00436 void appendMajorVectors(const int numvecs,
00437 const CoinPackedVectorBase * const * vecs);
00438
00440 void appendMinorVector(const CoinPackedVectorBase& vec);
00441 #endif
00442
00443 void appendMinorVector(const int vecsize, const int *vecind,
00444 const double *vecelem);
00445 #ifndef CLP_NO_VECTOR
00446
00447 void appendMinorVectors(const int numvecs,
00448 const CoinPackedVectorBase * const * vecs);
00449 #endif
00450
00451
00452
00465 void majorAppendSameOrdered(const CoinPackedMatrix& matrix);
00470 void minorAppendSameOrdered(const CoinPackedMatrix& matrix);
00476 void majorAppendOrthoOrdered(const CoinPackedMatrix& matrix);
00482 void minorAppendOrthoOrdered(const CoinPackedMatrix& matrix);
00484
00485
00490 void deleteMajorVectors(const int numDel, const int * indDel);
00493 void deleteMinorVectors(const int numDel, const int * indDel);
00495
00496
00503 void timesMajor(const double * x, double * y) const;
00504 #ifndef CLP_NO_VECTOR
00505
00508 void timesMajor(const CoinPackedVectorBase& x, double * y) const;
00509 #endif
00510
00514 void timesMinor(const double * x, double * y) const;
00515 #ifndef CLP_NO_VECTOR
00516
00519 void timesMinor(const CoinPackedVectorBase& x, double * y) const;
00520 #endif
00521
00522
00523
00524
00527 #ifndef CLP_NO_VECTOR
00528
00533 template <class FloatEqual> bool
00534 isEquivalent(const CoinPackedMatrix& rhs, const FloatEqual& eq) const
00535 {
00536
00537 if ((isColOrdered() ^ rhs.isColOrdered()) ||
00538 (getNumCols() != rhs.getNumCols()) ||
00539 (getNumRows() != rhs.getNumRows()) ||
00540 (getNumElements() != rhs.getNumElements()))
00541 return false;
00542
00543 for (int i=getMajorDim()-1; i >= 0; --i) {
00544 CoinShallowPackedVector pv = getVector(i);
00545 CoinShallowPackedVector rhsPv = rhs.getVector(i);
00546 if ( !pv.isEquivalent(rhsPv,eq) )
00547 return false;
00548 }
00549 return true;
00550 }
00551
00552 bool isEquivalent2(const CoinPackedMatrix& rhs) const;
00553 #else
00554
00559 bool isEquivalent(const CoinPackedMatrix& rhs, const CoinRelFltEq & eq) const;
00560 #endif
00562 bool isEquivalent(const CoinPackedMatrix& rhs) const
00563 {
00564 return isEquivalent(rhs, CoinRelFltEq());
00565 }
00567
00568
00576 inline double * getMutableElements() const { return element_; }
00582 inline int * getMutableIndices() const { return index_; }
00583
00586 inline CoinBigIndex * getMutableVectorStarts() const { return start_; }
00588 inline int * getMutableVectorLengths() const { return length_; }
00590 inline void nullElementArray() {element_=NULL;}
00592 inline void nullStartArray() {start_=NULL;}
00594 inline void nullLengthArray() {length_=NULL;}
00596 inline void nullIndexArray() {index_=NULL;}
00598
00599
00602
00603 CoinPackedMatrix();
00604
00606 CoinPackedMatrix(const bool colordered,
00607 const double extraMajor, const double extraGap);
00608
00609 CoinPackedMatrix(const bool colordered,
00610 const int minor, const int major, const CoinBigIndex numels,
00611 const double * elem, const int * ind,
00612 const CoinBigIndex * start, const int * len,
00613 const double extraMajor, const double extraGap);
00614
00615 CoinPackedMatrix(const bool colordered,
00616 const int minor, const int major, const CoinBigIndex numels,
00617 const double * elem, const int * ind,
00618 const CoinBigIndex * start, const int * len);
00619
00630 CoinPackedMatrix(const bool colordered,
00631 const int * rowIndices,
00632 const int * colIndices,
00633 const double * elements,
00634 CoinBigIndex numels );
00635
00637 CoinPackedMatrix(const CoinPackedMatrix& m);
00638
00641 CoinPackedMatrix (const CoinPackedMatrix & wholeModel,
00642 int numberRows, const int * whichRows,
00643 int numberColumns, const int * whichColumns);
00644
00646 virtual ~CoinPackedMatrix();
00648
00649
00650 protected:
00651 void gutsOfDestructor();
00652 void gutsOfCopyOf(const bool colordered,
00653 const int minor, const int major, const CoinBigIndex numels,
00654 const double * elem, const int * ind,
00655 const CoinBigIndex * start, const int * len,
00656 const double extraMajor=0.0, const double extraGap=0.0);
00658 void gutsOfCopyOfNoGaps(const bool colordered,
00659 const int minor, const int major,
00660 const double * elem, const int * ind,
00661 const CoinBigIndex * start);
00662 void gutsOfOpEqual(const bool colordered,
00663 const int minor, const int major, const CoinBigIndex numels,
00664 const double * elem, const int * ind,
00665 const CoinBigIndex * start, const int * len);
00666 void resizeForAddingMajorVectors(const int numVec, const int * lengthVec);
00667 void resizeForAddingMinorVectors(const int * addedEntries);
00672 int appendMajor(const int number,
00673 const CoinBigIndex * starts, const int * index,
00674 const double * element, int numberOther=-1);
00679 int appendMinor(const int number,
00680 const CoinBigIndex * starts, const int * index,
00681 const double * element, int numberOther=-1);
00682 private:
00683 inline CoinBigIndex getLastStart() const {
00684 return majorDim_ == 0 ? 0 : start_[majorDim_];
00685 }
00686
00687
00688 protected:
00693 bool colOrdered_;
00698 double extraGap_;
00702 double extraMajor_;
00703
00706 double *element_;
00709 int *index_;
00711 CoinBigIndex *start_;
00713 int *length_;
00714
00716 int majorDim_;
00718 int minorDim_;
00720 CoinBigIndex size_;
00721
00723 int maxMajorDim_;
00725 CoinBigIndex maxSize_;
00727 };
00728
00729
00735 void
00736 CoinPackedMatrixUnitTest();
00737
00738 #endif