00001
00002
00003
00004
00005
00006 #ifndef CoinWarmStartVector_H
00007 #define CoinWarmStartVector_H
00008
00009 #if defined(_MSC_VER)
00010
00011 # pragma warning(disable:4786)
00012 #endif
00013
00014 #include <cassert>
00015 #include <cmath>
00016
00017 #include "CoinHelperFunctions.hpp"
00018 #include "CoinWarmStart.hpp"
00019
00020
00021
00022
00025 template <typename T>
00026 class CoinWarmStartVector : public virtual CoinWarmStart
00027 {
00028 protected:
00029 inline void gutsOfDestructor() {
00030 delete[] values_;
00031 }
00032 inline void gutsOfCopy(const CoinWarmStartVector<T>& rhs) {
00033 size_ = rhs.size_;
00034 values_ = new T[size_];
00035 CoinDisjointCopyN(rhs.values_, size_, values_);
00036 }
00037
00038 public:
00040 int size() const { return size_; }
00042 const T* values() const { return values_; }
00043
00047 void assignVector(int size, T*& vec) {
00048 size_ = size;
00049 delete[] values_;
00050 values_ = vec;
00051 vec = NULL;
00052 }
00053
00054 CoinWarmStartVector() : size_(0), values_(NULL) {}
00055
00056 CoinWarmStartVector(int size, const T* vec) :
00057 size_(size), values_(new T[size]) {
00058 CoinDisjointCopyN(vec, size, values_);
00059 }
00060
00061 CoinWarmStartVector(const CoinWarmStartVector& rhs) {
00062 gutsOfCopy(rhs);
00063 }
00064
00065 CoinWarmStartVector& operator=(const CoinWarmStartVector& rhs) {
00066 if (this != &rhs) {
00067 gutsOfDestructor();
00068 gutsOfCopy(rhs);
00069 }
00070 return *this;
00071 }
00072
00073 inline void swap(CoinWarmStartVector& rhs) {
00074 if (this != &rhs) {
00075 std::swap(size_, rhs.size_);
00076 std::swap(values_, rhs.values_);
00077 }
00078 }
00079
00081 virtual CoinWarmStart *clone() const {
00082 return new CoinWarmStartVector(*this);
00083 }
00084
00085 virtual ~CoinWarmStartVector() {
00086 gutsOfDestructor();
00087 }
00088
00094 inline void clear() {
00095 size_ = 0;
00096 delete[] values_;
00097 values_ = NULL;
00098 }
00099
00102
00110 virtual CoinWarmStartDiff*
00111 generateDiff (const CoinWarmStart *const oldCWS) const ;
00112
00119 virtual void applyDiff (const CoinWarmStartDiff *const cwsdDiff) ;
00120
00122
00123 private:
00125
00126
00127 int size_;
00129 T* values_;
00131 };
00132
00133
00134
00150 template <typename T>
00151 class CoinWarmStartVectorDiff : public virtual CoinWarmStartDiff
00152 {
00153 friend CoinWarmStartDiff*
00154 CoinWarmStartVector<T>::generateDiff(const CoinWarmStart *const oldCWS) const;
00155 friend void
00156 CoinWarmStartVector<T>::applyDiff(const CoinWarmStartDiff *const diff) ;
00157
00158 public:
00159
00161 virtual CoinWarmStartDiff * clone() const {
00162 return new CoinWarmStartVectorDiff(*this) ;
00163 }
00164
00166 virtual CoinWarmStartVectorDiff &
00167 operator= (const CoinWarmStartVectorDiff<T>& rhs) ;
00168
00170 virtual ~CoinWarmStartVectorDiff() {
00171 delete[] diffNdxs_ ;
00172 delete[] diffVals_ ;
00173 }
00174
00175 inline void swap(CoinWarmStartVectorDiff& rhs) {
00176 if (this != &rhs) {
00177 std::swap(sze_, rhs.sze_);
00178 std::swap(diffNdxs_, rhs.diffNdxs_);
00179 std::swap(diffVals_, rhs.diffVals_);
00180 }
00181 }
00182
00185 CoinWarmStartVectorDiff () : sze_(0), diffNdxs_(0), diffVals_(NULL) {}
00186
00193 CoinWarmStartVectorDiff(const CoinWarmStartVectorDiff<T>& rhs) ;
00194
00196 CoinWarmStartVectorDiff(int sze, const unsigned int* const diffNdxs,
00197 const T* const diffVals) ;
00198
00204 inline void clear() {
00205 sze_ = 0;
00206 delete[] diffNdxs_; diffNdxs_ = NULL;
00207 delete[] diffVals_; diffVals_ = NULL;
00208 }
00209
00210 private:
00211
00215 int sze_ ;
00216
00219 unsigned int* diffNdxs_ ;
00220
00223 T* diffVals_ ;
00224 };
00225
00226
00227
00228 template <typename T, typename U>
00229 class CoinWarmStartVectorPair : public virtual CoinWarmStart
00230 {
00231 private:
00232 CoinWarmStartVector<T> t_;
00233 CoinWarmStartVector<U> u_;
00234
00235 public:
00236 inline int size0() const { return t_.size(); }
00237 inline int size1() const { return u_.size(); }
00238 inline const T* values0() const { return t_.values(); }
00239 inline const U* values1() const { return u_.values(); }
00240
00241 inline void assignVector0(int size, T*& vec) { t_.assignVector(size, vec); }
00242 inline void assignVector1(int size, U*& vec) { u_.assignVector(size, vec); }
00243
00244 CoinWarmStartVectorPair() {}
00245 CoinWarmStartVectorPair(int s0, const T* v0, int s1, const U* v1) :
00246 t_(s0, v0), u_(s1, v1) {}
00247
00248 CoinWarmStartVectorPair(const CoinWarmStartVectorPair<T,U>& rhs) :
00249 t_(rhs.t_), u_(rhs.u_) {}
00250 CoinWarmStartVectorPair& operator=(const CoinWarmStartVectorPair<T,U>& rhs) {
00251 if (this != &rhs) {
00252 t_ = rhs.t_;
00253 u_ = rhs.u_;
00254 }
00255 }
00256
00257 inline void swap(CoinWarmStartVectorPair<T,U>& rhs) {
00258 t_.swap(rhs.t_);
00259 u_.swap(rhs.u_);
00260 }
00261
00262 virtual CoinWarmStart *clone() const {
00263 return new CoinWarmStartVectorPair(*this);
00264 }
00265
00266 virtual ~CoinWarmStartVectorPair() {}
00267
00268 inline void clear() {
00269 t_.clear();
00270 u_.clear();
00271 }
00272
00273 virtual CoinWarmStartDiff*
00274 generateDiff (const CoinWarmStart *const oldCWS) const ;
00275
00276 virtual void applyDiff (const CoinWarmStartDiff *const cwsdDiff) ;
00277 };
00278
00279
00280
00281 template <typename T, typename U>
00282 class CoinWarmStartVectorPairDiff : public virtual CoinWarmStartDiff
00283 {
00284 friend CoinWarmStartDiff*
00285 CoinWarmStartVectorPair<T,U>::generateDiff(const CoinWarmStart *const oldCWS) const;
00286 friend void
00287 CoinWarmStartVectorPair<T,U>::applyDiff(const CoinWarmStartDiff *const diff) ;
00288
00289 private:
00290 CoinWarmStartVectorDiff<T> tdiff_;
00291 CoinWarmStartVectorDiff<U> udiff_;
00292
00293 public:
00294 CoinWarmStartVectorPairDiff() {}
00295 CoinWarmStartVectorPairDiff(const CoinWarmStartVectorPairDiff<T,U>& rhs) :
00296 tdiff_(rhs.tdiff_), udiff_(rhs.udiff_) {}
00297 ~CoinWarmStartVectorPairDiff() {}
00298
00299 virtual CoinWarmStartVectorPairDiff&
00300 operator=(const CoinWarmStartVectorPairDiff<T,U>& rhs) {
00301 tdiff_ = rhs.tdiff_;
00302 udiff_ = rhs.udiff_;
00303 }
00304
00305 virtual CoinWarmStartDiff * clone() const {
00306 return new CoinWarmStartVectorPairDiff(*this) ;
00307 }
00308
00309 inline void swap(CoinWarmStartVectorPairDiff<T,U>& rhs) {
00310 tdiff_.swap(rhs.tdiff_);
00311 udiff_.swap(rhs.udiff_);
00312 }
00313
00314 inline void clear() {
00315 tdiff_.clear();
00316 udiff_.clear();
00317 }
00318 };
00319
00320
00321
00322
00323
00324
00325
00326
00327
00328
00329
00330
00331 template <typename T> CoinWarmStartDiff*
00332 CoinWarmStartVector<T>::generateDiff(const CoinWarmStart *const oldCWS) const
00333 {
00334
00335
00336
00337 const CoinWarmStartVector<T>* oldVector =
00338 dynamic_cast<const CoinWarmStartVector<T>*>(oldCWS);
00339 if (!oldVector)
00340 { throw CoinError("Old warm start not derived from CoinWarmStartVector.",
00341 "generateDiff","CoinWarmStartVector") ; }
00342 const CoinWarmStartVector<T>* newVector = this ;
00343
00344
00345
00346
00347 const int oldCnt = oldVector->size() ;
00348 const int newCnt = newVector->size() ;
00349
00350 assert(newCnt >= oldCnt) ;
00351
00352 unsigned int *diffNdx = new unsigned int [newCnt];
00353 T* diffVal = new T[newCnt];
00354
00355
00356
00357
00358 const T*oldVal = oldVector->values() ;
00359 const T*newVal = newVector->values() ;
00360 int numberChanged = 0 ;
00361 int i ;
00362 for (i = 0 ; i < oldCnt ; i++) {
00363 if (oldVal[i] != newVal[i]) {
00364 diffNdx[numberChanged] = i ;
00365 diffVal[numberChanged++] = newVal[i] ;
00366 }
00367 }
00368 for ( ; i < newCnt ; i++) {
00369 diffNdx[numberChanged] = i ;
00370 diffVal[numberChanged++] = newVal[i] ;
00371 }
00372
00373
00374
00375 CoinWarmStartVectorDiff<T> *diff =
00376 new CoinWarmStartVectorDiff<T>(numberChanged,diffNdx,diffVal) ;
00377
00378
00379
00380 delete[] diffNdx ;
00381 delete[] diffVal ;
00382
00383 return diff;
00384
00385 }
00386
00387
00388
00389
00390
00391
00392
00393
00394
00395 template <typename T> void
00396 CoinWarmStartVector<T>::applyDiff (const CoinWarmStartDiff *const cwsdDiff)
00397 {
00398
00399
00400
00401 const CoinWarmStartVectorDiff<T>* diff =
00402 dynamic_cast<const CoinWarmStartVectorDiff<T>*>(cwsdDiff) ;
00403 if (!diff) {
00404 throw CoinError("Diff not derived from CoinWarmStartVectorDiff.",
00405 "applyDiff","CoinWarmStartVector") ;
00406 }
00407
00408
00409
00410 const int numberChanges = diff->sze_ ;
00411 const unsigned int *diffNdxs = diff->diffNdxs_ ;
00412 const T* diffVals = diff->diffVals_ ;
00413 T* vals = this->values_ ;
00414
00415 for (int i = 0 ; i < numberChanges ; i++) {
00416 unsigned int diffNdx = diffNdxs[i] ;
00417 T diffVal = diffVals[i] ;
00418 vals[diffNdx] = diffVal ;
00419 }
00420 }
00421
00422
00423
00424
00425
00426
00427 template <typename T> CoinWarmStartVectorDiff<T>&
00428 CoinWarmStartVectorDiff<T>::operator=(const CoinWarmStartVectorDiff<T> &rhs)
00429 {
00430 if (this != &rhs) {
00431 if (sze_ > 0) {
00432 delete[] diffNdxs_ ;
00433 delete[] diffVals_ ;
00434 }
00435 sze_ = rhs.sze_ ;
00436 if (sze_ > 0) {
00437 diffNdxs_ = new unsigned int[sze_] ;
00438 memcpy(diffNdxs_,rhs.diffNdxs_,sze_*sizeof(unsigned int)) ;
00439 diffVals_ = new T[sze_] ;
00440 memcpy(diffVals_,rhs.diffVals_,sze_*sizeof(T)) ;
00441 } else {
00442 diffNdxs_ = 0 ;
00443 diffVals_ = 0 ;
00444 }
00445 }
00446
00447 return (*this) ;
00448 }
00449
00450
00451
00452
00453 template <typename T>
00454 CoinWarmStartVectorDiff<T>::CoinWarmStartVectorDiff(const CoinWarmStartVectorDiff<T> &rhs)
00455 : sze_(rhs.sze_),
00456 diffNdxs_(0),
00457 diffVals_(0)
00458 {
00459 if (sze_ > 0) {
00460 diffNdxs_ = new unsigned int[sze_] ;
00461 memcpy(diffNdxs_,rhs.diffNdxs_,sze_*sizeof(unsigned int)) ;
00462 diffVals_ = new T[sze_] ;
00463 memcpy(diffVals_,rhs.diffVals_,sze_*sizeof(T)) ;
00464 }
00465 }
00466
00468
00469 template <typename T>
00470 CoinWarmStartVectorDiff<T>::CoinWarmStartVectorDiff
00471 (int sze, const unsigned int *const diffNdxs, const T *const diffVals)
00472 : sze_(sze),
00473 diffNdxs_(0),
00474 diffVals_(0)
00475 {
00476 if (sze > 0) {
00477 diffNdxs_ = new unsigned int[sze] ;
00478 memcpy(diffNdxs_,diffNdxs,sze*sizeof(unsigned int)) ;
00479 diffVals_ = new T[sze] ;
00480 memcpy(diffVals_,diffVals,sze*sizeof(T)) ;
00481 }
00482 }
00483
00484 #endif