00001 #ifdef CH_LANG_CC
00002
00003
00004
00005
00006
00007
00008
00009 #endif
00010
00011 #ifndef _INDEXTMI_H_
00012 #define _INDEXTMI_H_
00013
00014 #include <iostream>
00015 using std::ostream;
00016 using std::istream;
00017 using std::ws;
00018
00019 #include "MayDay.H"
00020 #include "Misc.H"
00021 #include "IndexTM.H"
00022 #include "parstream.H"
00023 #include <cmath>
00024 #include <algorithm>
00025 #include <functional>
00026 #include <numeric>
00027 #include "Metaprograms.H"
00028
00029 #include "BaseNamespaceHeader.H"
00030
00031 template<typename T, int N> ostream& operator<< (ostream & a_os,
00032 const IndexTM<T,N> & a_p)
00033 {
00034 a_os << '(';
00035
00036 for (int i = 0; i < N; ++i)
00037 {
00038 a_os << a_p[i];
00039
00040 if (i < N-1)
00041 {
00042 a_os << ',';
00043 }
00044 }
00045
00046 a_os << ')';
00047
00048 if (a_os.fail())
00049 {
00050 MayDay::Abort("operator<<(ostream&,Index&) failed");
00051 }
00052
00053 return a_os;
00054 }
00055
00056
00057
00058
00059 #define CH_IGNORE_MAX 100000
00060
00061 template<typename T, int N> istream& operator>> (istream & a_is,
00062 IndexTM<T,N> & a_p)
00063 {
00064 a_is >> ws;
00065
00066 char c;
00067 a_is >> c;
00068 a_is.putback(c);
00069
00070 if (c == '(')
00071 {
00072 a_is.ignore(CH_IGNORE_MAX, '(') >> a_p[0];
00073
00074 for (int i = 1; i < N; ++i)
00075 {
00076 a_is.ignore(CH_IGNORE_MAX, ',') >> a_p[i];
00077 }
00078
00079 a_is.ignore(CH_IGNORE_MAX, ')');
00080 }
00081 else if (c == '<')
00082 {
00083 a_is.ignore(CH_IGNORE_MAX, '<') >> a_p[0];
00084
00085 for (int i = 1; i < N; ++i)
00086 {
00087 a_is.ignore(CH_IGNORE_MAX, ',') >> a_p[1];
00088 }
00089 a_is.ignore(CH_IGNORE_MAX, '>');
00090 }
00091 else
00092 {
00093 MayDay::Abort("operator>>(istream&,Index&): expected \'(\' or \'<\'");
00094 }
00095
00096 if (a_is.fail())
00097 {
00098 MayDay::Abort("operator>>(istream&,Index&) failed");
00099 }
00100
00101 return a_is;
00102 }
00103
00104 template<typename T, int N> void IndexTM<T,N>::printOn (ostream & a_os) const
00105 {
00106 a_os << "Index: " << *this << "\n";
00107 }
00108
00109 template<typename T, int N> void IndexTM<T,N>::p() const
00110 {
00111 pout() << *this << "\n";
00112 }
00113
00114 template<typename T, int N> void IndexTM<T,N>::dumpOn (ostream & a_os) const
00115 {
00116 a_os << "Index " << *this << "\n";
00117 }
00118
00119
00120
00121
00122
00123
00124
00125
00126
00127
00128
00129
00130
00131
00132
00133
00134
00135
00136
00137
00138
00139
00140
00141
00142
00143
00144
00145
00146
00147
00148 template<typename T, int N> inline IndexTM<T,N>::IndexTM(const T *a_a)
00149 : GenericArithmeticable< T, IndexTM<T,N> >(this)
00150 {
00151 memcpy(m_vect, a_a, N*sizeof(T));
00152 }
00153
00154 template<typename T, int N> inline IndexTM<T,N>::IndexTM(const char* a_reference)
00155 : GenericArithmeticable< T, IndexTM<T,N> >(this)
00156 {
00157 if (a_reference[0] == 48) setAll(0);
00158 else if (a_reference[0] == 49) setAll(1);
00159 else
00160 MayDay::Error("unknown static initialization for IndexTM");
00161 }
00162
00163 template<typename T, int N> inline IndexTM<T,N>::IndexTM(const IndexTM<T,N> & a_iv)
00164 : GenericArithmeticable< T, IndexTM<T,N> >(this)
00165 {
00166 memcpy(m_vect, a_iv.m_vect, N*sizeof(T));
00167 }
00168
00169 template<typename T, int N> inline IndexTM<T,N>& IndexTM<T,N>::operator=(const IndexTM<T,N> & a_iv)
00170 {
00171 memcpy(m_vect, a_iv.m_vect, N*sizeof(T));
00172 return *this;
00173 }
00174
00175 template<typename T, int N> inline T& IndexTM<T,N>::operator[] (int a_i)
00176 {
00177 CH_assert(a_i >= 0 && a_i < N);
00178 return m_vect[a_i];
00179 }
00180
00181 template<typename T, int N> inline T IndexTM<T,N>::operator[] (int a_i) const
00182 {
00183 CH_assert(a_i >= 0 && a_i < N);
00184 return m_vect[a_i];
00185 }
00186
00187 template<typename T, int N> inline void IndexTM<T,N>::setVal(int a_i,
00188 T a_val)
00189 {
00190 CH_assert(a_i >= 0 && a_i < N);
00191 m_vect[a_i] = a_val;
00192 }
00193
00194 template<typename T, int N> inline void IndexTM<T,N>::setAll(T a_val)
00195 {
00196 for (int i = 0; i < N; i++)
00197 {
00198 m_vect[i] = a_val;
00199 }
00200 }
00201
00202 template<typename T, int N> inline const T* IndexTM<T,N>::dataPtr() const
00203 {
00204 return m_vect;
00205 }
00206
00207 template<typename T, int N> inline T* IndexTM<T,N>::dataPtr()
00208 {
00209 return m_vect;
00210 }
00211
00212 template<typename T, int N> inline const T* IndexTM<T,N>::getVect() const
00213 {
00214 return m_vect;
00215 }
00216
00217 template<typename T, int N> inline bool IndexTM<T,N>::operator== (const IndexTM & a_p) const
00218 {
00219 return Metaprograms::pointwiseCompare<N,T,std::equal_to<T> >(m_vect,a_p.m_vect);
00220 }
00221
00222 template<typename T, int N> inline bool IndexTM<T,N>::operator!= (const IndexTM & a_p) const
00223 {
00224 return !(operator==(a_p));
00225 }
00226
00227 template<typename T, int N> inline bool IndexTM<T,N>::lexLT(const IndexTM & a_s) const
00228 {
00229 return Metaprograms::LexLT<N,T>()(m_vect,a_s.m_vect);
00230 }
00231
00232 template<typename T, int N> inline bool IndexTM<T,N>::lexGT(const IndexTM & a_s) const
00233 {
00234 return ! Metaprograms::LexLT<N,T>()(m_vect,a_s.m_vect);
00235 }
00236
00237 template<typename T, int N> inline IndexTM<T,N> IndexTM<T,N>::operator+ () const
00238 {
00239 return IndexTM<T,N>(*this);
00240 }
00241
00242 template<typename T, int N> inline IndexTM<T,N> IndexTM<T,N>::operator- () const
00243 {
00244 IndexTM<T,N> result(*this);
00245 for (int i = 0; i < N; ++i)
00246 {
00247 result.m_vect[i] *= -1;
00248 }
00249 return result;
00250 }
00251
00252 template<typename T, int N> inline T IndexTM<T,N>::dotProduct(const IndexTM<T,N> & a_rhs ) const
00253 {
00254 return Metaprograms::InnerProduct<N,T,T,
00255 std::plus<T>,
00256 std::multiplies<T> >()(m_vect,
00257 a_rhs.m_vect);
00258 }
00259
00260 template<typename T, int N> inline T IndexTM<T,N>::sum() const
00261 {
00262 return Metaprograms::Accum<N,T,std::plus<T> >()(m_vect);
00263 }
00264
00265 template<typename T, int N> inline T IndexTM<T,N>::product () const
00266 {
00267 return Metaprograms::Accum<N,T,std::multiplies<T> >()(m_vect);
00268 }
00269
00270 template<typename T, int N> template<typename OP> bool IndexTM<T,N>::operatorCompare(const IndexTM<T,N> & a_p,
00271 const OP & a_op) const
00272 {
00273 return Metaprograms::pointwiseCompare<N,T,OP>(m_vect,a_p.m_vect);
00274 }
00275
00276 template<typename T, int N> template<typename OP> inline IndexTM<T,N>& IndexTM<T,N>::operatorOpEquals(const T & a_s,
00277 const OP & a_op)
00278 {
00279 Metaprograms::Transform<N,T,OP>()(m_vect,a_s);
00280 return *this;
00281 }
00282
00283 template<typename T, int N> template<typename OP> inline IndexTM<T,N>& IndexTM<T,N>::operatorOpEquals(const IndexTM<T,N> & a_p,
00284 const OP & a_op)
00285 {
00286 Metaprograms::Transform<N,T,OP>()(m_vect,a_p.m_vect);
00287 return *this;
00288 }
00289
00290 template<typename T, int N> inline IndexTM<T,N>& IndexTM<T,N>::reciprocal()
00291 {
00292 std::transform(m_vect, m_vect+N, m_vect, bind1st(std::divides<T>(),T(1)));
00293 return *this;
00294 }
00295
00296 template<typename T> static bool abscompare(const T & a_a,
00297 const T & a_b)
00298 {
00299 return Abs(a_a) < Abs(a_b);
00300 }
00301 template<typename T, int N> inline int IndexTM<T,N>::minDir(bool a_doAbs) const
00302 {
00303 if (a_doAbs)
00304 {
00305 return std::min_element(m_vect, m_vect+N, std::ptr_fun(abscompare<T>)) - m_vect;
00306 }
00307 else
00308 {
00309 return std::min_element(m_vect, m_vect+N) - m_vect;
00310 }
00311 }
00312
00313 template<typename T, int N> inline int IndexTM<T,N>::maxDir(bool a_doAbs) const
00314 {
00315 if (a_doAbs)
00316 {
00317 return std::max_element(m_vect, m_vect+N, std::ptr_fun(abscompare<T>)) - m_vect;
00318 }
00319 else
00320 {
00321 return std::max_element(m_vect, m_vect+N) - m_vect;
00322 }
00323 }
00324
00325 template<typename T> static T ourmin(T a_a,
00326 T a_b)
00327 {
00328 return ((a_a < a_b) ? a_a : a_b);
00329 }
00330
00331 template<typename T> static T ourmax(T a_a,
00332 T a_b)
00333 {
00334 return (a_a > a_b ? a_a : a_b);
00335 }
00336
00337 template<typename T, int N> inline IndexTM<T,N>& IndexTM<T,N>::min(const IndexTM<T,N> & a_p)
00338 {
00339 std::transform(m_vect, m_vect+N, a_p.m_vect, m_vect,
00340 std::ptr_fun(ourmin<T>));
00341 return *this;
00342 }
00343
00344 template<typename T, int N> inline IndexTM<T,N>& IndexTM<T,N>::max(const IndexTM<T,N> & a_p)
00345 {
00346 std::transform(m_vect, m_vect+N, a_p.m_vect, m_vect,
00347 std::ptr_fun(ourmax<T>));
00348 return *this;
00349 }
00350
00351 template<typename T, int N> inline IndexTM<T,N>& IndexTM<T,N>::scale(T a_s)
00352 {
00353 return (*this) *= a_s;
00354 }
00355
00356 template<typename T, int N> inline IndexTM<T,N>& IndexTM<T,N>::reflect (T a_refIx,
00357 int a_idir)
00358 {
00359 CH_assert(a_idir >= 0 && a_idir < N);
00360 m_vect[a_idir] = -m_vect[a_idir] + 2*a_refIx;
00361 return *this;
00362 }
00363
00364 template<typename T, int N> inline IndexTM<T,N>& IndexTM<T,N>::shift(int a_coord,
00365 T a_s)
00366 {
00367 CH_assert(a_coord >= 0 && a_coord < N);
00368 m_vect[a_coord] += a_s;
00369 return *this;
00370 }
00371
00372 template<typename T, int N> inline IndexTM<T,N>& IndexTM<T,N>::shift(const IndexTM<T,N> & a_iv)
00373 {
00374 return (*this) += a_iv;
00375 }
00376
00377 template<typename T, int N> inline IndexTM<T,N>& IndexTM<T,N>::diagShift(T a_s)
00378 {
00379 return (*this) += a_s;
00380 }
00381
00382 template<typename T, int N> inline IndexTM<T,N> scale (const IndexTM<T,N> & a_p,
00383 T a_s)
00384 {
00385 return a_p * a_s;
00386 }
00387
00388 template<typename T, int N> inline IndexTM<T,N> diagShift(const IndexTM<T,N> & a_p,
00389 T a_s)
00390 {
00391 return a_p + a_s;
00392 }
00393
00394 template<typename T, int N> inline IndexTM<T,N> min(const IndexTM<T,N> & a_p1,
00395 const IndexTM<T,N> & a_p2)
00396 {
00397 IndexTM<T,N> result(a_p1);
00398 return result.min(a_p2);
00399 }
00400
00401 template<typename T, int N> inline IndexTM<T,N> max(const IndexTM<T,N> & a_p1,
00402 const IndexTM<T,N> & a_p2)
00403 {
00404 IndexTM<T,N> result(a_p1);
00405 return result.max(a_p2);
00406 }
00407
00408 template<typename T, int N> inline IndexTM<T,N> BASISV_TM(int a_dir)
00409 {
00410 CH_assert(a_dir >= 0 && a_dir < N);
00411 IndexTM<T,N> tmp = IndexTM<T,N>::Zero ;
00412 tmp.dataPtr()[a_dir] = T(1);
00413 return tmp;
00414 }
00415
00416 template<typename T, int N> inline IndexTM<T,N> reflect(const IndexTM<T,N> & a_a,
00417 T a_refIx,
00418 int a_idir)
00419 {
00420 IndexTM<T,N> result(a_a);
00421 return result.reflect(a_refIx, a_idir);
00422 }
00423
00424 template<typename T> static T ourcoarsen(T a_a,
00425 T a_b)
00426 {
00427 return (a_a < 0 ? T(-Abs(a_a+1))/a_b-1 : a_a/a_b);
00428 }
00429
00430 template<typename T, int N> inline IndexTM<T,N> coarsen(const IndexTM<T,N> & a_p,
00431 T a_s)
00432 {
00433 IndexTM<T,N> result(a_p);
00434 return result.coarsen(a_s);
00435 }
00436
00437 template<typename T, int N> inline IndexTM<T,N> coarsen(const IndexTM<T,N> & a_p1,
00438 const IndexTM<T,N> & a_p2)
00439 {
00440 IndexTM<T,N> result(a_p1);
00441 return result.coarsen(a_p2);
00442 }
00443
00444
00445
00446
00447
00448
00449
00450
00451
00452
00453
00454
00455
00456 template<typename T, int N> inline IndexTM<T,N>& IndexTM<T,N>::coarsen(T a_s)
00457 {
00458 CH_assert(a_s > 0);
00459 std::transform(m_vect, m_vect+N, m_vect,
00460 std::bind2nd(std::ptr_fun(ourcoarsen<T>),a_s));
00461 return *this;
00462 }
00463
00464 template<typename T, int N> inline IndexTM<T,N>& IndexTM<T,N>::coarsen(const IndexTM<T,N> & a_p)
00465 {
00466 CH_assert(a_p > (IndexTM<T,N>::Zero));
00467 std::transform(m_vect, m_vect+N, a_p.m_vect, m_vect, std::ptr_fun(ourcoarsen<T>));
00468 return *this;
00469 }
00470
00471 template<typename T, int N> void IndexTM<T,N>::linearIn(const void* a_inBuf)
00472 {
00473 memcpy(m_vect, (T*)a_inBuf, N*sizeof(T));
00474 }
00475
00476 template<typename T, int N> void IndexTM<T,N>::linearOut(void* a_outBuf) const
00477 {
00478 memcpy((T*)a_outBuf, m_vect, N*sizeof(T));
00479 }
00480
00481 template<typename T, int N> IndexTM<T,N>::IndexTM(T a_i)
00482 : GenericArithmeticable< T, IndexTM<T,N> >(this)
00483 {
00484 static_assert(N == 1,"N==1");
00485 m_vect[0] = a_i;
00486 }
00487
00488 template<typename T, int N> IndexTM<T,N>::IndexTM(T a_i,
00489 T a_j)
00490 : GenericArithmeticable< T, IndexTM<T,N> >(this)
00491 {
00492 static_assert(N == 2, "N==2");
00493 m_vect[0] = a_i;
00494 m_vect[1] = a_j;
00495 }
00496
00497 template<typename T, int N> IndexTM<T,N>::IndexTM(T a_i,
00498 T a_j,
00499 T a_k)
00500 : GenericArithmeticable< T, IndexTM<T,N> >(this)
00501 {
00502 static_assert(N == 3, "N==3");
00503 m_vect[0] = a_i;
00504 m_vect[1] = a_j;
00505 m_vect[2] = a_k;
00506 }
00507
00508 template<typename T, int N> IndexTM<T,N>::IndexTM(T a_i,
00509 T a_j,
00510 T a_k,
00511 T a_l)
00512 : GenericArithmeticable< T, IndexTM<T,N> >(this)
00513 {
00514 static_assert(N == 4, "N==4");
00515 m_vect[0] = a_i;
00516 m_vect[1] = a_j;
00517 m_vect[2] = a_k;
00518 m_vect[3] = a_l;
00519 }
00520
00521 template<typename T, int N> IndexTM<T,N>::IndexTM(T a_i,
00522 T a_j,
00523 T a_k,
00524 T a_l,
00525 T a_m)
00526 : GenericArithmeticable< T, IndexTM<T,N> >(this)
00527 {
00528 static_assert(N == 5, "N==5");
00529 m_vect[0] = a_i;
00530 m_vect[1] = a_j;
00531 m_vect[2] = a_k;
00532 m_vect[3] = a_l;
00533 m_vect[4] = a_m;
00534 }
00535
00536 template<typename T, int N> IndexTM<T,N>::IndexTM(T a_i,
00537 T a_j,
00538 T a_k,
00539 T a_l,
00540 T a_m,
00541 T a_n)
00542 : GenericArithmeticable< T, IndexTM<T,N> >(this)
00543 {
00544 static_assert(N == 6, "N==6");
00545 m_vect[0] = a_i;
00546 m_vect[1] = a_j;
00547 m_vect[2] = a_k;
00548 m_vect[3] = a_l;
00549 m_vect[4] = a_m;
00550 m_vect[5] = a_n;
00551 }
00552
00553
00554
00555
00556
00557
00558
00559
00560
00561
00562
00563
00564
00565
00566
00567
00568
00569
00570
00571
00572
00573
00574
00575
00576
00577
00578
00579
00580 #include "BaseNamespaceFooter.H"
00581
00582 #endif // include guard