00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011 #ifndef BARE_FIELD_ITERATOR_H
00012 #define BARE_FIELD_ITERATOR_H
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027 #include "Index/NDIndex.h"
00028 #include "Field/LField.h"
00029 #include "Field/FieldLoc.h"
00030 #include "Field/CompressedBrickIterator.h"
00031 #include "Field/BrickIterator.h"
00032 #include "Utility/IpplInfo.h"
00033 #include "Utility/PAssert.h"
00034
00035
00036 template<class T, unsigned Dim> class BareField;
00037
00038
00039 template<class T, unsigned Dim>
00040 class BareFieldIterator
00041 : public CompressedBrickIterator<T,Dim>
00042 {
00043 public:
00044
00045 typedef T return_type;
00046
00047
00048 BareFieldIterator()
00049 : CompressedBrickIterator<T,Dim>(dummy_compressed_data),
00050 LFIndex(-1),
00051 MyBareField(0)
00052 {
00053
00054
00055 }
00056
00057
00058
00059 BareFieldIterator(BareField<T,Dim> &df)
00060 : CompressedBrickIterator<T,Dim>(dummy_compressed_data),
00061 LFIndex(0),
00062 CurrentLField(df.begin_if()),
00063 MyBareField(&df)
00064 {
00065
00066 beginLField();
00067
00068
00069
00070 }
00071
00072
00073
00074
00075 BareFieldIterator(const FieldLoc<Dim> &loc, BareField<T,Dim> &df)
00076 : CompressedBrickIterator<T,Dim>(dummy_compressed_data),
00077 LFIndex(0),
00078 CurrentLField(df.begin_if()),
00079 MyBareField(&df)
00080 {
00081
00082 SetCurrentLocation(loc);
00083
00084
00085
00086 }
00087
00088
00089 BareFieldIterator(const BareFieldIterator<T,Dim> &iter)
00090 : CompressedBrickIterator<T,Dim>(iter),
00091 LFIndex(iter.LFIndex),
00092 CurrentLField(iter.CurrentLField),
00093 MyBareField(iter.MyBareField)
00094 {
00095
00096
00097 }
00098
00099
00100 ~BareFieldIterator()
00101 {
00102 }
00103
00104
00105 const BareFieldIterator<T,Dim> &
00106 operator=(const BareFieldIterator<T,Dim> &rhs)
00107 {
00108
00109 if (this == &rhs)
00110 return *this;
00111
00112
00113 *(dynamic_cast<CompressedBrickIterator<T,Dim>*>(this)) = rhs;
00114
00115
00116 LFIndex = rhs.LFIndex;
00117 CurrentLField = rhs.CurrentLField;
00118 MyBareField = rhs.MyBareField;
00119
00120 return *this;
00121 }
00122
00123
00124 void SetCurrentLocation(const FieldLoc<Dim> &loc)
00125 {
00126
00127
00128 PAssert(MyBareField != NULL);
00129 CurrentLField = MyBareField->begin_if();
00130 LFIndex = 0;
00131
00132
00133
00134 int curr = loc.getIndex();
00135 while (!done() && curr-- > 0)
00136 nextLField();
00137
00138 if (!done()) {
00139
00140 const NDIndex<Dim>& domain = (*CurrentLField).second->getOwned();
00141 int offloc[Dim];
00142 for (unsigned int d=0; d < Dim; ++d)
00143 offloc[d] = (loc[d] - domain[d].first()) / domain[d].stride();
00144
00145
00146 beginLField();
00147 moveBy(offloc);
00148 } else {
00149 IpplInfo::abort("Inconsistent FieldLoc in SetCurrentLocation.");
00150 }
00151 }
00152
00153
00154 void GetCurrentLocation(FieldLoc<Dim> &loc) const
00155 {
00156 const NDIndex<Dim>& domain = (*CurrentLField).second->getOwned();
00157 for (unsigned d=0; d<Dim; ++d)
00158 loc[d] = this->GetOffset(d)*domain[d].stride() + domain[d].first();
00159 loc.setIndex(LFIndex);
00160 }
00161
00162
00163 void GetCurrentLocation(int *loc) const
00164 {
00165 const NDIndex<Dim>& domain = (*CurrentLField).second->getOwned();
00166 for (unsigned d=0; d<Dim; ++d)
00167 loc[d] = this->GetOffset(d)*domain[d].stride() + domain[d].first();
00168 }
00169
00170
00171 BareFieldIterator<T,Dim>& operator++()
00172 {
00173 CompressedBrickIterator<T,Dim>::operator++();
00174 if ( *this == (*CurrentLField).second->end() )
00175 general_increment();
00176 return *this;
00177 }
00178
00179
00180 T& operator*() const
00181 {
00182 PAssert(MyBareField != NULL);
00183
00184
00185 return CompressedBrickIterator<T,Dim>::operator*();
00186 }
00187
00188
00189 void nextLField()
00190 {
00191 ++CurrentLField; ++LFIndex;
00192 }
00193
00194
00195 bool done() const
00196 {
00197 PAssert(MyBareField != NULL);
00198 return CurrentLField == MyBareField->end_if();
00199 }
00200
00201
00202 bool done(unsigned d) const
00203 {
00204 return CompressedBrickIterator<T,Dim>::done(d);
00205 }
00206
00207
00208 void beginLField()
00209 {
00210 if (!done())
00211 *(CompressedBrickIterator<T,Dim>*)this =
00212 (*CurrentLField).second->begin();
00213 else
00214 LFIndex = (-1);
00215 }
00216
00217
00218 bool IsCompressed() const
00219 {
00220 bool is_compressed = CompressedBrickIterator<T,Dim>::IsCompressed();
00221 PAssert((*CurrentLField).second->IsCompressed() == is_compressed);
00222 return is_compressed;
00223 }
00224
00225
00226 bool CanCompress() const
00227 {
00228 PAssert(MyBareField != NULL);
00229 if (!MyBareField->compressible()) return false;
00230 return (*CurrentLField).second->CanCompress();
00231 }
00232
00233
00234 void Compress()
00235 {
00236 (*CurrentLField).second->Compress();
00237 }
00238
00239
00240 void Compress(T val)
00241 {
00242 (*CurrentLField).second->Compress(val);
00243 }
00244
00245
00246 bool TryCompress()
00247 {
00248 return (*CurrentLField).second->TryCompress();
00249 }
00250
00251
00252 BareField<T,Dim> &GetBareField()
00253 {
00254 PAssert(MyBareField != NULL);
00255 return *MyBareField;
00256 }
00257
00258
00259 const BareField<T,Dim> &GetBareField() const
00260 {
00261 PAssert(MyBareField != NULL);
00262 return *MyBareField;
00263 }
00264
00265
00266
00267
00268
00269
00270
00271
00272
00273
00274
00275
00276
00277 void prepareForScalarCode(bool tryfill = true)
00278 {
00279 PAssert(MyBareField != NULL);
00280 MyBareField->prepareForScalarCode(tryfill);
00281 }
00282
00283
00284
00285
00286
00287
00288 void finishScalarCode(bool modified = true)
00289 {
00290 PAssert(MyBareField != NULL);
00291 MyBareField->finishScalarCode(modified);
00292 }
00293
00294 protected:
00295
00296 typename BareField<T,Dim>::iterator_if CurrentLField;
00297
00298
00299 BareField<T,Dim>* MyBareField;
00300
00301
00302 T dummy_compressed_data;
00303
00304
00305 int LFIndex;
00306
00307
00308
00309
00310 void general_increment()
00311 {
00312 nextLField();
00313 beginLField();
00314 }
00315
00316
00317
00318 bool isInGC() const
00319 {
00320
00321 const NDIndex<Dim> &owned = (*CurrentLField).second->getOwned();
00322
00323
00324 for (unsigned d=0; d<Dim; ++d)
00325 {
00326 unsigned locd = this->GetOffset(d)*owned[d].stride() + owned[d].first();
00327 if (!owned[d].contains(Index(locd,locd)))
00328 return true;
00329 }
00330
00331
00332 return false;
00333 }
00334 };
00335
00336
00337 #endif // BARE_FIELD_ITERATOR_H
00338
00339
00340
00341
00342
00343