00001
00029 #ifndef ABA_ARRAY_INC
00030 #define ABA_ARRAY_INC
00031
00032 #ifdef ABACUS_PARALLEL
00033 #include "abacus/message.h"
00034 #include "abacus/fsvarstat.h"
00035 #include "abacus/lpvarstat.h"
00036 #include "abacus/slackstat.h"
00037 #endif
00038
00039 using std::endl;
00040 template <class Type>
00041 inline ABA_ARRAY<Type>::ABA_ARRAY(ABA_GLOBAL *glob, int size)
00042 :
00043 glob_(glob),
00044 n_(size)
00045 {
00046 #ifdef ABACUSSAFE
00047 if (size < 0) {
00048 glob_->err() << "ABA_ARRAY::ABA_ARRAY(): cannot construct array with negative size" << endl;
00049 exit(Fatal);
00050 }
00051 #endif
00052 a_ = new Type[size];
00053 }
00054
00055 template <class Type>
00056 ABA_ARRAY<Type>::ABA_ARRAY(ABA_GLOBAL *glob, int size, Type init)
00057 :
00058 glob_(glob),
00059 n_(size)
00060 {
00061 #ifdef ABACUSSAFE
00062 if (size < 0) {
00063 glob_->err() << "ABA_ARRAY::ABA_ARRAY(): cannot construct array with negative size" << endl;
00064 exit(Fatal);
00065 }
00066 #endif
00067
00068 a_ = new Type[size];
00069 set(init);
00070 }
00071
00072 template <class Type>
00073 ABA_ARRAY<Type>::ABA_ARRAY(ABA_GLOBAL *glob, const ABA_BUFFER<Type> &buf)
00074 :
00075 glob_(glob),
00076 n_(buf.number())
00077 {
00078 a_ = new Type[n_] ;
00079 for (int i = 0; i < n_; i++) a_[i] = buf[i];
00080 }
00081
00082 template <class Type>
00083 ABA_ARRAY<Type>::ABA_ARRAY(const ABA_ARRAY<Type> &rhs)
00084 :
00085 glob_(rhs.glob_),
00086 n_(rhs.n_)
00087 {
00088 a_ = new Type[n_];
00089 for (int i = 0; i < n_; i++) a_[i] = rhs[i];
00090 }
00091
00092 template <class Type>
00093 inline ABA_ARRAY<Type>::~ABA_ARRAY()
00094 {
00095 delete [] a_;
00096 }
00097
00098 #ifdef ABACUS_PARALLEL
00099
00100 template <class Type>
00101 ABA_ARRAY<Type>::ABA_ARRAY(const ABA_GLOBAL *glob, ABA_MESSAGE &msg)
00102 :
00103 glob_(glob),
00104 n_(0),
00105 a_(0)
00106 {
00107 glob_->err() << "ABA_ARRAY::ABA_ARRAY() : An ABA_ARRAY of some type coudn't"
00108 " be received. You have to implement a template"
00109 " specialization of the message constructor for"
00110 " that type!" << endl;
00111 exit(Fatal);
00112 }
00113
00114 template<class Type>
00115 void ABA_ARRAY<Type>::pack(ABA_MESSAGE &msg) const
00116 {
00117 pack(msg, n_);
00118 }
00119
00120 template<class Type>
00121 void ABA_ARRAY<Type>::pack(ABA_MESSAGE &msg, int nPacked) const
00122 {
00123 glob_->err() << "ABA_ARRAY::pack() : An ABA_ARRAY of some type coudn't"
00124 " be sent. You first have to implement a template"
00125 " specialization of the pack() template function"
00126 " for that type!" << endl;
00127 exit(Fatal);
00128 }
00129
00130 #endif
00131
00132 template <class Type>
00133 const ABA_ARRAY<Type>& ABA_ARRAY<Type>::operator=(const ABA_ARRAY<Type>& rhs)
00134 {
00135 if (this == &rhs) return *this;
00136
00137
00138
00139
00140
00141 if (n_ != rhs.n_) {
00142 glob_->err() << "ABA_ARRAY::operator= : dimensions of left and right hand side ";
00143 glob_->err() << "are different (" << n_ << " != " << rhs.n_ << ")" << endl;
00144 exit(Fatal);
00145 }
00146
00147 glob_ = rhs.glob_;
00148 n_ = rhs.n_;
00149
00150 for (int i = 0; i < n_; i++) a_[i] = rhs[i];
00151
00152 return *this;
00153 }
00154
00155 template <class Type>
00156 const ABA_ARRAY<Type>& ABA_ARRAY<Type>::operator=(const ABA_BUFFER<Type>& rhs)
00157 {
00158 if (n_ < rhs.size()) {
00159 glob_->err() << "ABA_ARRAY::operator=(const ABA_BUFFER&): ";
00160 glob_->err() << "size of ABA_ARRAY too small." << endl;
00161 exit(Fatal);
00162 }
00163
00164 const int rhsNumber = rhs.number();
00165
00166 for (int i = 0; i < rhsNumber; i++) a_[i] = rhs[i];
00167
00168 return *this;
00169
00170 }
00171
00172 template <class Type>
00173 ostream& operator<<(ostream &out, const ABA_ARRAY<Type> &array)
00174 {
00175 const int s = array.size();
00176
00177 for (int i = 0; i < s; i++) out << i << ": " << array[i] << endl;
00178 return out;
00179 }
00180
00181 template <class Type>
00182 inline Type& ABA_ARRAY<Type>::operator[](int i)
00183 {
00184 #ifdef ABACUSSAFE
00185 rangeCheck(i);
00186 #endif
00187
00188 return a_[i];
00189 }
00190
00191 template <class Type>
00192 inline const Type& ABA_ARRAY<Type>::operator[](int i) const
00193 {
00194
00195 #ifdef ABACUSSAFE
00196 rangeCheck(i);
00197 #endif
00198
00199 return a_[i];
00200
00201 }
00202
00203 template<class Type>
00204 void ABA_ARRAY<Type>::copy(const ABA_ARRAY<Type> &rhs)
00205 {
00206 copy(rhs, 0, rhs.size() - 1);
00207 }
00208
00209 template<class Type>
00210 void ABA_ARRAY<Type>::copy(const ABA_ARRAY<Type> &rhs, int l, int r)
00211 {
00212
00213 if (r < l) {
00214 glob_->err() << "ABA_ARRAY::copy() : r = " << r << " is less than ";
00215 glob_->err() << "r = " << r << endl;
00216 exit (Fatal);
00217 }
00218
00219
00220 if (n_ < r-l+1) {
00221 delete [] a_;
00222 n_ = r-l+1;
00223 a_ = new Type[n_];
00224 }
00225
00226
00227 for (int i = 0; i <= r-l; i++) a_[i] = rhs[l + i];
00228
00229 }
00230
00231 template <class Type>
00232 void ABA_ARRAY<Type>::leftShift(ABA_BUFFER<int> &ind)
00233 {
00234 const int nInd = ind.number();
00235
00236 if (nInd == 0) return;
00237
00238 int i,j;
00239 int current = ind[0];
00240
00241
00242
00243 #ifdef ABACUSSAFE
00244 if(ind[0] < 0 || ind[0] >= n_) {
00245 glob_->err() << "ABA_ARRAY:leftShift(): shift index " << 0 << " not valid." << endl;
00246 exit(Fatal);
00247 }
00248 #endif
00249
00250 for (i = 0; i < nInd - 1; i++) {
00251
00252 #ifdef ABACUSSAFE
00253 if(ind[i+1] < 0 || ind[i+1] >= n_) {
00254 glob_->err() << "ABA_ARRAY:leftShift(): shift index " << i+1 << " not valid." << endl;
00255 exit(Fatal);
00256 }
00257 #endif
00258
00259 const int last = ind[i+1];
00260 for(j = ind[i]+1; j < last; j++)
00261 a_[current++] = a_[j];
00262 }
00263
00264
00265 for (j = ind[nInd - 1] + 1; j < n_; j++)
00266 a_[current++] = a_[j];
00267 }
00268
00269 template <class Type>
00270 void ABA_ARRAY<Type>::leftShift(ABA_ARRAY<bool> &remove)
00271 {
00272 ABA_BUFFER<int> removeIndex(glob_, n_);
00273
00274 for (int i = 0; i < n_; i++)
00275 if (remove[i])
00276 removeIndex.push(i);
00277
00278 leftShift(removeIndex);
00279 }
00280
00281 template <class Type>
00282 void ABA_ARRAY<Type>::set(int l, int r, Type val)
00283 {
00284 for (int i = l; i <= r; i++) a_[i] = val;
00285 }
00286
00287 template <class Type>
00288 void ABA_ARRAY<Type>::set(Type val)
00289 {
00290 set(0, n_ - 1, val);
00291 }
00292
00293 template <class Type>
00294 void ABA_ARRAY<Type>::rangeCheck(int i) const
00295 {
00296 if (i < 0 || i >= n_) {
00297 glob_->err() << "ABA_ARRAY:operator[] : index " << i;
00298 glob_->err() << " out of ranges [0," << n_-1 << "]" << endl;
00299 exit(Fatal);
00300 }
00301 }
00302
00303 template <class Type>
00304 inline int ABA_ARRAY<Type>::size() const
00305 {
00306 return n_;
00307 }
00308
00309 template <class Type>
00310 void ABA_ARRAY<Type>::realloc(int newSize)
00311 {
00312 if (newSize != n_) {
00313 Type *newA = new Type[newSize];
00314
00315 int length = n_ < newSize ? n_ : newSize;
00316
00317 for (int i = 0; i < length; i++) newA[i] = a_[i];
00318
00319 delete [] a_;
00320
00321 a_ = newA;
00322 n_ = newSize;
00323 }
00324 }
00325
00326 template <class Type>
00327 void ABA_ARRAY<Type>::realloc(int newSize, Type init)
00328 {
00329 if (newSize != n_) {
00330 delete [] a_;
00331
00332 a_ = new Type[newSize];
00333 n_ = newSize;
00334 }
00335
00336 set(init);
00337 }
00338
00339 #endif // ABA_ARRAY_INC