CoinUtils trunk
|
00001 /* $Id$ */ 00002 // Copyright (C) 2000, International Business Machines 00003 // Corporation and others. All Rights Reserved. 00004 // This code is licensed under the terms of the Eclipse Public License (EPL). 00005 00006 #ifndef CoinIndexedVector_H 00007 #define CoinIndexedVector_H 00008 00009 #if defined(_MSC_VER) 00010 // Turn off compiler warning about long names 00011 # pragma warning(disable:4786) 00012 #endif 00013 00014 #include <map> 00015 #ifndef CLP_NO_VECTOR 00016 #include "CoinPackedVectorBase.hpp" 00017 #endif 00018 #include "CoinSort.hpp" 00019 #include "CoinHelperFunctions.hpp" 00020 #include <cassert> 00021 00022 #ifndef COIN_FLOAT 00023 #define COIN_INDEXED_TINY_ELEMENT 1.0e-50 00024 #define COIN_INDEXED_REALLY_TINY_ELEMENT 1.0e-100 00025 #else 00026 #define COIN_INDEXED_TINY_ELEMENT 1.0e-35 00027 #define COIN_INDEXED_REALLY_TINY_ELEMENT 1.0e-39 00028 #endif 00029 00103 class CoinIndexedVector { 00104 friend void CoinIndexedVectorUnitTest(); 00105 00106 public: 00109 00110 inline int getNumElements() const { return nElements_; } 00112 inline const int * getIndices() const { return indices_; } 00114 // ** No longer supported virtual const double * getElements() const ; 00116 inline int * getIndices() { return indices_; } 00120 inline double * denseVector() const { return elements_; } 00122 inline void setDenseVector(double * array) 00123 { elements_ = array;} 00125 inline void setIndexVector(int * array) 00126 { indices_ = array;} 00129 double & operator[](int i) const; 00130 00132 00133 //------------------------------------------------------------------- 00134 // Set indices and elements 00135 //------------------------------------------------------------------- 00138 00139 inline void setNumElements(int value) { nElements_ = value; 00140 if (!nElements_) packedMode_=false;} 00142 void clear(); 00144 void empty(); 00146 CoinIndexedVector & operator=(const CoinIndexedVector &); 00147 #ifndef CLP_NO_VECTOR 00148 00150 CoinIndexedVector & operator=(const CoinPackedVectorBase & rhs); 00151 #endif 00152 00155 void copy(const CoinIndexedVector & rhs, double multiplier=1.0); 00156 00159 void borrowVector(int size, int numberIndices, int* inds, double* elems); 00160 00164 void returnVector(); 00165 00170 void setVector(int numberIndices, const int * inds, const double * elems); 00171 00176 void setVector(int size, int numberIndices, const int * inds, const double * elems); 00177 00179 void setConstant(int size, const int * inds, double elems); 00180 00182 void setFull(int size, const double * elems); 00183 00187 void setElement(int index, double element); 00188 00190 void insert(int index, double element); 00193 void add(int index, double element); 00197 inline void quickAdd(int index, double element) 00198 { 00199 if (elements_[index]) { 00200 element += elements_[index]; 00201 if ((element > 0 ? element : -element) >= COIN_INDEXED_TINY_ELEMENT) { 00202 elements_[index] = element; 00203 } else { 00204 elements_[index] = 1.0e-100; 00205 } 00206 } else if ((element > 0 ? element : -element) >= COIN_INDEXED_TINY_ELEMENT) { 00207 indices_[nElements_++] = index; 00208 assert (nElements_<=capacity_); 00209 elements_[index] = element; 00210 } 00211 } 00214 inline void zero(int index) 00215 { 00216 if (elements_[index]) 00217 elements_[index] = 1.0e-100; 00218 } 00221 int clean(double tolerance); 00223 int cleanAndPack(double tolerance); 00225 int cleanAndPackSafe(double tolerance); 00227 inline void setPacked() 00228 { packedMode_ = true;} 00230 void checkClear(); 00232 void checkClean(); 00234 int scan(); 00238 int scan(int start, int end); 00241 int scan(double tolerance); 00245 int scan(int start, int end, double tolerance); 00247 int scanAndPack(); 00248 int scanAndPack(int start, int end); 00249 int scanAndPack(double tolerance); 00250 int scanAndPack(int start, int end, double tolerance); 00252 void createPacked(int number, const int * indices, 00253 const double * elements); 00255 void expand(); 00256 #ifndef CLP_NO_VECTOR 00257 00258 void append(const CoinPackedVectorBase & caboose); 00259 #endif 00260 00261 void append(const CoinIndexedVector & caboose); 00262 00264 void swap(int i, int j); 00265 00267 void truncate(int newSize); 00269 void print() const; 00271 00273 00274 void operator+=(double value); 00276 void operator-=(double value); 00278 void operator*=(double value); 00280 void operator/=(double value); 00282 00285 #ifndef CLP_NO_VECTOR 00286 00288 bool operator==(const CoinPackedVectorBase & rhs) const; 00290 bool operator!=(const CoinPackedVectorBase & rhs) const; 00291 #endif 00292 00294 bool operator==(const CoinIndexedVector & rhs) const; 00296 bool operator!=(const CoinIndexedVector & rhs) const; 00298 00301 00302 int getMaxIndex() const; 00304 int getMinIndex() const; 00306 00307 00311 void sort() 00312 { std::sort(indices_,indices_+nElements_); } 00313 00314 void sortIncrIndex() 00315 { std::sort(indices_,indices_+nElements_); } 00316 00317 void sortDecrIndex(); 00318 00319 void sortIncrElement(); 00320 00321 void sortDecrElement(); 00322 00324 00325 //############################################################################# 00326 00338 00339 CoinIndexedVector operator+( 00340 const CoinIndexedVector& op2); 00341 00343 CoinIndexedVector operator-( 00344 const CoinIndexedVector& op2); 00345 00347 CoinIndexedVector operator*( 00348 const CoinIndexedVector& op2); 00349 00351 CoinIndexedVector operator/( 00352 const CoinIndexedVector& op2); 00354 void operator+=(const CoinIndexedVector& op2); 00355 00357 void operator-=( const CoinIndexedVector& op2); 00358 00360 void operator*=(const CoinIndexedVector& op2); 00361 00363 void operator/=(const CoinIndexedVector& op2); 00365 00372 void reserve(int n); 00376 int capacity() const { return capacity_; } 00378 inline void setPackedMode(bool yesNo) 00379 { packedMode_=yesNo;} 00381 inline bool packedMode() const 00382 { return packedMode_;} 00384 00388 CoinIndexedVector(); 00390 CoinIndexedVector(int size, const int * inds, const double * elems); 00392 CoinIndexedVector(int size, const int * inds, double element); 00395 CoinIndexedVector(int size, const double * elements); 00397 CoinIndexedVector(int size); 00399 CoinIndexedVector(const CoinIndexedVector &); 00401 CoinIndexedVector(const CoinIndexedVector *); 00402 #ifndef CLP_NO_VECTOR 00403 00404 CoinIndexedVector(const CoinPackedVectorBase & rhs); 00405 #endif 00406 00407 ~CoinIndexedVector (); 00409 00410 private: 00413 00414 void gutsOfSetVector(int size, 00415 const int * inds, const double * elems); 00416 void gutsOfSetVector(int size, int numberIndices, 00417 const int * inds, const double * elems); 00418 void gutsOfSetPackedVector(int size, int numberIndices, 00419 const int * inds, const double * elems); 00421 void gutsOfSetConstant(int size, 00422 const int * inds, double value); 00424 00425 private: 00428 00429 int * indices_; 00431 double * elements_; 00433 int nElements_; 00435 int capacity_; 00437 int offset_; 00439 bool packedMode_; 00441 }; 00442 00443 //############################################################################# 00449 void 00450 CoinIndexedVectorUnitTest(); 00467 class CoinArrayWithLength { 00468 00469 public: 00472 00473 inline int getSize() const 00474 { return size_; } 00476 inline int rawSize() const 00477 { return size_; } 00479 inline bool switchedOn() const 00480 { return size_!=-1; } 00482 inline int getCapacity() const 00483 { return (size_>-2) ? size_ : (-size_)-2; } 00485 inline void setCapacity() 00486 { if (size_<=-2) size_ = (-size_)-2; } 00488 inline const char * array() const 00489 { return (size_>-2) ? array_ : NULL; } 00491 00494 00495 inline void setSize(int value) 00496 { size_ = value; } 00498 inline void switchOff() 00499 { size_ = -1; } 00501 void setPersistence(int flag,int currentLength); 00503 void clear(); 00505 void swap(CoinArrayWithLength & other); 00507 void extend(int newSize); 00509 00512 00513 char * conditionalNew(long sizeWanted); 00515 void conditionalDelete(); 00517 00521 inline CoinArrayWithLength() 00522 { array_=NULL; size_=-1;} 00524 inline CoinArrayWithLength(int size) 00525 { array_=new char [size]; size_=-1;} 00530 inline CoinArrayWithLength(int size, int mode) 00531 { array_ = new char [size]; if (mode) memset(array_,0,size);size_=size;} 00533 CoinArrayWithLength(const CoinArrayWithLength & rhs); 00535 CoinArrayWithLength(const CoinArrayWithLength * rhs); 00537 CoinArrayWithLength& operator=(const CoinArrayWithLength & rhs); 00539 void copy(const CoinArrayWithLength & rhs, int numberBytes=-1); 00541 void allocate(const CoinArrayWithLength & rhs, int numberBytes); 00543 inline ~CoinArrayWithLength () 00544 { delete [] array_; } 00545 // was { free(array_); } 00547 00548 protected: 00551 00552 char * array_; 00554 int size_; 00556 }; 00558 00559 class CoinDoubleArrayWithLength : public CoinArrayWithLength { 00560 00561 public: 00564 00565 inline int getSize() const 00566 { return size_/CoinSizeofAsInt(double); } 00568 inline double * array() const 00569 { return reinterpret_cast<double *> ((size_>-2) ? array_ : NULL); } 00571 00574 00575 inline void setSize(int value) 00576 { size_ = value*CoinSizeofAsInt(double); } 00578 00581 00582 inline double * conditionalNew(int sizeWanted) 00583 { return reinterpret_cast<double *> ( CoinArrayWithLength::conditionalNew(sizeWanted>=0 ? static_cast<long> ((sizeWanted)*CoinSizeofAsInt(double)) : -1)); } 00585 00589 inline CoinDoubleArrayWithLength() 00590 { array_=NULL; size_=-1;} 00592 inline CoinDoubleArrayWithLength(int size) 00593 { array_=new char [size*CoinSizeofAsInt(double)]; size_=-1;} 00598 inline CoinDoubleArrayWithLength(int size, int mode) 00599 : CoinArrayWithLength(size*CoinSizeofAsInt(double),mode) {} 00601 inline CoinDoubleArrayWithLength(const CoinDoubleArrayWithLength & rhs) 00602 : CoinArrayWithLength(rhs) {} 00604 inline CoinDoubleArrayWithLength(const CoinDoubleArrayWithLength * rhs) 00605 : CoinArrayWithLength(rhs) {} 00607 inline CoinDoubleArrayWithLength& operator=(const CoinDoubleArrayWithLength & rhs) 00608 { CoinArrayWithLength::operator=(rhs); return *this;} 00610 }; 00612 00613 class CoinFactorizationDoubleArrayWithLength : public CoinArrayWithLength { 00614 00615 public: 00618 00619 inline int getSize() const 00620 { return size_/CoinSizeofAsInt(CoinFactorizationDouble); } 00622 inline CoinFactorizationDouble * array() const 00623 { return reinterpret_cast<CoinFactorizationDouble *> ((size_>-2) ? array_ : NULL); } 00625 00628 00629 inline void setSize(int value) 00630 { size_ = value*CoinSizeofAsInt(CoinFactorizationDouble); } 00632 00635 00636 inline CoinFactorizationDouble * conditionalNew(int sizeWanted) 00637 { return reinterpret_cast<CoinFactorizationDouble *> (CoinArrayWithLength::conditionalNew(sizeWanted>=0 ? static_cast<long> (( sizeWanted)*CoinSizeofAsInt(CoinFactorizationDouble)) : -1)); } 00639 00643 inline CoinFactorizationDoubleArrayWithLength() 00644 { array_=NULL; size_=-1;} 00646 inline CoinFactorizationDoubleArrayWithLength(int size) 00647 { array_=new char [size*CoinSizeofAsInt(CoinFactorizationDouble)]; size_=-1;} 00652 inline CoinFactorizationDoubleArrayWithLength(int size, int mode) 00653 : CoinArrayWithLength(size*CoinSizeofAsInt(CoinFactorizationDouble),mode) {} 00655 inline CoinFactorizationDoubleArrayWithLength(const CoinFactorizationDoubleArrayWithLength & rhs) 00656 : CoinArrayWithLength(rhs) {} 00658 inline CoinFactorizationDoubleArrayWithLength(const CoinFactorizationDoubleArrayWithLength * rhs) 00659 : CoinArrayWithLength(rhs) {} 00661 inline CoinFactorizationDoubleArrayWithLength& operator=(const CoinFactorizationDoubleArrayWithLength & rhs) 00662 { CoinArrayWithLength::operator=(rhs); return *this;} 00664 }; 00666 00667 class CoinIntArrayWithLength : public CoinArrayWithLength { 00668 00669 public: 00672 00673 inline int getSize() const 00674 { return size_/CoinSizeofAsInt(int); } 00676 inline int * array() const 00677 { return reinterpret_cast<int *> ((size_>-2) ? array_ : NULL); } 00679 00682 00683 inline void setSize(int value) 00684 { size_ = value*CoinSizeofAsInt(int); } 00686 00689 00690 inline int * conditionalNew(int sizeWanted) 00691 { return reinterpret_cast<int *> (CoinArrayWithLength::conditionalNew(sizeWanted>=0 ? static_cast<long> (( sizeWanted)*CoinSizeofAsInt(int)) : -1)); } 00693 00697 inline CoinIntArrayWithLength() 00698 { array_=NULL; size_=-1;} 00700 inline CoinIntArrayWithLength(int size) 00701 { array_=new char [size*CoinSizeofAsInt(int)]; size_=-1;} 00706 inline CoinIntArrayWithLength(int size, int mode) 00707 : CoinArrayWithLength(size*CoinSizeofAsInt(int),mode) {} 00709 inline CoinIntArrayWithLength(const CoinIntArrayWithLength & rhs) 00710 : CoinArrayWithLength(rhs) {} 00712 inline CoinIntArrayWithLength(const CoinIntArrayWithLength * rhs) 00713 : CoinArrayWithLength(rhs) {} 00715 inline CoinIntArrayWithLength& operator=(const CoinIntArrayWithLength & rhs) 00716 { CoinArrayWithLength::operator=(rhs); return *this;} 00718 }; 00720 00721 class CoinBigIndexArrayWithLength : public CoinArrayWithLength { 00722 00723 public: 00726 00727 inline int getSize() const 00728 { return size_/CoinSizeofAsInt(CoinBigIndex); } 00730 inline CoinBigIndex * array() const 00731 { return reinterpret_cast<CoinBigIndex *> ((size_>-2) ? array_ : NULL); } 00733 00736 00737 inline void setSize(int value) 00738 { size_ = value*CoinSizeofAsInt(CoinBigIndex); } 00740 00743 00744 inline CoinBigIndex * conditionalNew(int sizeWanted) 00745 { return reinterpret_cast<CoinBigIndex *> (CoinArrayWithLength::conditionalNew(sizeWanted>=0 ? static_cast<long> (( sizeWanted)*CoinSizeofAsInt(CoinBigIndex)) : -1)); } 00747 00751 inline CoinBigIndexArrayWithLength() 00752 { array_=NULL; size_=-1;} 00754 inline CoinBigIndexArrayWithLength(int size) 00755 { array_=new char [size*CoinSizeofAsInt(CoinBigIndex)]; size_=-1;} 00760 inline CoinBigIndexArrayWithLength(int size, int mode) 00761 : CoinArrayWithLength(size*CoinSizeofAsInt(CoinBigIndex),mode) {} 00763 inline CoinBigIndexArrayWithLength(const CoinBigIndexArrayWithLength & rhs) 00764 : CoinArrayWithLength(rhs) {} 00766 inline CoinBigIndexArrayWithLength(const CoinBigIndexArrayWithLength * rhs) 00767 : CoinArrayWithLength(rhs) {} 00769 inline CoinBigIndexArrayWithLength& operator=(const CoinBigIndexArrayWithLength & rhs) 00770 { CoinArrayWithLength::operator=(rhs); return *this;} 00772 }; 00774 00775 class CoinUnsignedIntArrayWithLength : public CoinArrayWithLength { 00776 00777 public: 00780 00781 inline int getSize() const 00782 { return size_/CoinSizeofAsInt(unsigned int); } 00784 inline unsigned int * array() const 00785 { return reinterpret_cast<unsigned int *> ((size_>-2) ? array_ : NULL); } 00787 00790 00791 inline void setSize(int value) 00792 { size_ = value*CoinSizeofAsInt(unsigned int); } 00794 00797 00798 inline unsigned int * conditionalNew(int sizeWanted) 00799 { return reinterpret_cast<unsigned int *> (CoinArrayWithLength::conditionalNew(sizeWanted>=0 ? static_cast<long> (( sizeWanted)*CoinSizeofAsInt(unsigned int)) : -1)); } 00801 00805 inline CoinUnsignedIntArrayWithLength() 00806 { array_=NULL; size_=-1;} 00808 inline CoinUnsignedIntArrayWithLength(int size) 00809 { array_=new char [size*CoinSizeofAsInt(unsigned int)]; size_=-1;} 00814 inline CoinUnsignedIntArrayWithLength(int size, int mode) 00815 : CoinArrayWithLength(size*CoinSizeofAsInt(unsigned int),mode) {} 00817 inline CoinUnsignedIntArrayWithLength(const CoinUnsignedIntArrayWithLength & rhs) 00818 : CoinArrayWithLength(rhs) {} 00820 inline CoinUnsignedIntArrayWithLength(const CoinUnsignedIntArrayWithLength * rhs) 00821 : CoinArrayWithLength(rhs) {} 00823 inline CoinUnsignedIntArrayWithLength& operator=(const CoinUnsignedIntArrayWithLength & rhs) 00824 { CoinArrayWithLength::operator=(rhs); return *this;} 00826 }; 00827 #endif