Blender V2.61 - r43446
|
00001 00004 /* 00005 00006 * 00007 * Template Numerical Toolkit (TNT): Linear Algebra Module 00008 * 00009 * Mathematical and Computational Sciences Division 00010 * National Institute of Technology, 00011 * Gaithersburg, MD USA 00012 * 00013 * 00014 * This software was developed at the National Institute of Standards and 00015 * Technology (NIST) by employees of the Federal Government in the course 00016 * of their official duties. Pursuant to title 17 Section 105 of the 00017 * United States Code, this software is not subject to copyright protection 00018 * and is in the public domain. The Template Numerical Toolkit (TNT) is 00019 * an experimental system. NIST assumes no responsibility whatsoever for 00020 * its use by other parties, and makes no guarantees, expressed or implied, 00021 * about its quality, reliability, or any other characteristic. 00022 * 00023 * BETA VERSION INCOMPLETE AND SUBJECT TO CHANGE 00024 * see http://math.nist.gov/tnt for latest updates. 00025 * 00026 */ 00027 00028 00029 00030 00031 #ifndef REGION1D_H 00032 #define REGION1D_H 00033 00034 00035 #include "subscript.h" 00036 #include "index.h" 00037 #include <iostream> 00038 #include <cassert> 00039 00040 namespace TNT 00041 { 00042 00043 template <class Array1D> 00044 class const_Region1D; 00045 00046 template <class Array1D> 00047 class Region1D 00048 { 00049 protected: 00050 00051 Array1D & A_; 00052 Subscript offset_; // 0-based 00053 Subscript dim_; 00054 00055 typedef typename Array1D::element_type T; 00056 00057 public: 00058 const Array1D & array() const { return A_; } 00059 00060 Subscript offset() const { return offset_;} 00061 Subscript dim() const { return dim_; } 00062 00063 Subscript offset(Subscript i) const 00064 { 00065 #ifdef TNT_BOUNDS_CHECK 00066 assert(i==TNT_BASE_OFFSET); 00067 #endif 00068 return offset_; 00069 } 00070 00071 Subscript dim(Subscript i) const 00072 { 00073 #ifdef TNT_BOUNDS_CHECK 00074 assert(i== TNT_BASE_OFFSET); 00075 #endif 00076 return offset_; 00077 } 00078 00079 00080 Region1D(Array1D &A, Subscript i1, Subscript i2) : A_(A) 00081 { 00082 #ifdef TNT_BOUNDS_CHECK 00083 assert(TNT_BASE_OFFSET <= i1 ); 00084 assert(i2 <= A.dim() + (TNT_BASE_OFFSET-1)); 00085 assert(i1 <= i2); 00086 #endif 00087 offset_ = i1 - TNT_BASE_OFFSET; 00088 dim_ = i2-i1 + 1; 00089 } 00090 00091 Region1D(Array1D &A, const Index1D &I) : A_(A) 00092 { 00093 #ifdef TNT_BOUNDS_CHECK 00094 assert(TNT_BASE_OFFSET <=I.lbound()); 00095 assert(I.ubound() <= A.dim() + (TNT_BASE_OFFSET-1)); 00096 assert(I.lbound() <= I.ubound()); 00097 #endif 00098 offset_ = I.lbound() - TNT_BASE_OFFSET; 00099 dim_ = I.ubound() - I.lbound() + 1; 00100 } 00101 00102 Region1D(Region1D<Array1D> &A, Subscript i1, Subscript i2) : 00103 A_(A.A_) 00104 { 00105 #ifdef TNT_BOUNDS_CHECK 00106 assert(TNT_BASE_OFFSET <= i1 ); 00107 assert(i2 <= A.dim() + (TNT_BASE_OFFSET - 1)); 00108 assert(i1 <= i2); 00109 #endif 00110 // (old-offset) (new-offset) 00111 // 00112 offset_ = (i1 - TNT_BASE_OFFSET) + A.offset_; 00113 dim_ = i2-i1 + 1; 00114 } 00115 00116 Region1D<Array1D> operator()(Subscript i1, Subscript i2) 00117 { 00118 #ifdef TNT_BOUNDS_CHECK 00119 assert(TNT_BASE_OFFSET <= i1); 00120 assert(i2 <= dim() + (TNT_BASE_OFFSET -1)); 00121 assert(i1 <= i2); 00122 #endif 00123 // offset_ is 0-based, so no need for 00124 // ( - TNT_BASE_OFFSET) 00125 // 00126 return Region1D<Array1D>(A_, i1+offset_, 00127 offset_ + i2); 00128 } 00129 00130 00131 Region1D<Array1D> operator()(const Index1D &I) 00132 { 00133 #ifdef TNT_BOUNDS_CHECK 00134 assert(TNT_BASE_OFFSET<=I.lbound()); 00135 assert(I.ubound() <= dim() + (TNT_BASE_OFFSET-1)); 00136 assert(I.lbound() <= I.ubound()); 00137 #endif 00138 return Region1D<Array1D>(A_, I.lbound()+offset_, 00139 offset_ + I.ubound()); 00140 } 00141 00142 00143 00144 00145 T & operator()(Subscript i) 00146 { 00147 #ifdef TNT_BOUNDS_CHECK 00148 assert(TNT_BASE_OFFSET <= i); 00149 assert(i <= dim() + (TNT_BASE_OFFSET-1)); 00150 #endif 00151 return A_(i+offset_); 00152 } 00153 00154 const T & operator() (Subscript i) const 00155 { 00156 #ifdef TNT_BOUNDS_CHECK 00157 assert(TNT_BASE_OFFSET <= i); 00158 assert(i <= dim() + (TNT_BASE_OFFSET-1)); 00159 #endif 00160 return A_(i+offset_); 00161 } 00162 00163 00164 Region1D<Array1D> & operator=(const Region1D<Array1D> &R) 00165 { 00166 // make sure both sides conform 00167 assert(dim() == R.dim()); 00168 00169 Subscript N = dim(); 00170 Subscript i; 00171 Subscript istart = TNT_BASE_OFFSET; 00172 Subscript iend = istart + N-1; 00173 00174 for (i=istart; i<=iend; i++) 00175 (*this)(i) = R(i); 00176 00177 return *this; 00178 } 00179 00180 00181 00182 Region1D<Array1D> & operator=(const const_Region1D<Array1D> &R) 00183 { 00184 // make sure both sides conform 00185 assert(dim() == R.dim()); 00186 00187 Subscript N = dim(); 00188 Subscript i; 00189 Subscript istart = TNT_BASE_OFFSET; 00190 Subscript iend = istart + N-1; 00191 00192 for (i=istart; i<=iend; i++) 00193 (*this)(i) = R(i); 00194 00195 return *this; 00196 00197 } 00198 00199 00200 Region1D<Array1D> & operator=(const T& t) 00201 { 00202 Subscript N=dim(); 00203 Subscript i; 00204 Subscript istart = TNT_BASE_OFFSET; 00205 Subscript iend = istart + N-1; 00206 00207 for (i=istart; i<= iend; i++) 00208 (*this)(i) = t; 00209 00210 return *this; 00211 00212 } 00213 00214 00215 Region1D<Array1D> & operator=(const Array1D &R) 00216 { 00217 // make sure both sides conform 00218 Subscript N = dim(); 00219 assert(dim() == R.dim()); 00220 00221 Subscript i; 00222 Subscript istart = TNT_BASE_OFFSET; 00223 Subscript iend = istart + N-1; 00224 00225 for (i=istart; i<=iend; i++) 00226 (*this)(i) = R(i); 00227 00228 return *this; 00229 00230 } 00231 00232 }; 00233 00234 template <class Array1D> 00235 std::ostream& operator<<(std::ostream &s, Region1D<Array1D> &A) 00236 { 00237 Subscript N=A.dim(); 00238 Subscript istart = TNT_BASE_OFFSET; 00239 Subscript iend = N - 1 + TNT_BASE_OFFSET; 00240 00241 for (Subscript i=istart; i<=iend; i++) 00242 s << A(i) << endl; 00243 00244 return s; 00245 } 00246 00247 00248 /* --------- class const_Region1D ------------ */ 00249 00250 template <class Array1D> 00251 class const_Region1D 00252 { 00253 protected: 00254 00255 const Array1D & A_; 00256 Subscript offset_; // 0-based 00257 Subscript dim_; 00258 typedef typename Array1D::element_type T; 00259 00260 public: 00261 const Array1D & array() const { return A_; } 00262 00263 Subscript offset() const { return offset_;} 00264 Subscript dim() const { return dim_; } 00265 00266 Subscript offset(Subscript i) const 00267 { 00268 #ifdef TNT_BOUNDS_CHECK 00269 assert(i==TNT_BASE_OFFSET); 00270 #endif 00271 return offset_; 00272 } 00273 00274 Subscript dim(Subscript i) const 00275 { 00276 #ifdef TNT_BOUNDS_CHECK 00277 assert(i== TNT_BASE_OFFSET); 00278 #endif 00279 return offset_; 00280 } 00281 00282 00283 const_Region1D(const Array1D &A, Subscript i1, Subscript i2) : A_(A) 00284 { 00285 #ifdef TNT_BOUNDS_CHECK 00286 assert(TNT_BASE_OFFSET <= i1 ); 00287 assert(i2 <= A.dim() + (TNT_BASE_OFFSET-1)); 00288 assert(i1 <= i2); 00289 #endif 00290 offset_ = i1 - TNT_BASE_OFFSET; 00291 dim_ = i2-i1 + 1; 00292 } 00293 00294 const_Region1D(const Array1D &A, const Index1D &I) : A_(A) 00295 { 00296 #ifdef TNT_BOUNDS_CHECK 00297 assert(TNT_BASE_OFFSET <=I.lbound()); 00298 assert(I.ubound() <= A.dim() + (TNT_BASE_OFFSET-1)); 00299 assert(I.lbound() <= I.ubound()); 00300 #endif 00301 offset_ = I.lbound() - TNT_BASE_OFFSET; 00302 dim_ = I.ubound() - I.lbound() + 1; 00303 } 00304 00305 const_Region1D(const_Region1D<Array1D> &A, Subscript i1, Subscript i2) : 00306 A_(A.A_) 00307 { 00308 #ifdef TNT_BOUNDS_CHECK 00309 assert(TNT_BASE_OFFSET <= i1 ); 00310 assert(i2 <= A.dim() + (TNT_BASE_OFFSET - 1)); 00311 assert(i1 <= i2); 00312 #endif 00313 // (old-offset) (new-offset) 00314 // 00315 offset_ = (i1 - TNT_BASE_OFFSET) + A.offset_; 00316 dim_ = i2-i1 + 1; 00317 } 00318 00319 const_Region1D<Array1D> operator()(Subscript i1, Subscript i2) 00320 { 00321 #ifdef TNT_BOUNDS_CHECK 00322 assert(TNT_BASE_OFFSET <= i1); 00323 assert(i2 <= dim() + (TNT_BASE_OFFSET -1)); 00324 assert(i1 <= i2); 00325 #endif 00326 // offset_ is 0-based, so no need for 00327 // ( - TNT_BASE_OFFSET) 00328 // 00329 return const_Region1D<Array1D>(A_, i1+offset_, 00330 offset_ + i2); 00331 } 00332 00333 00334 const_Region1D<Array1D> operator()(const Index1D &I) 00335 { 00336 #ifdef TNT_BOUNDS_CHECK 00337 assert(TNT_BASE_OFFSET<=I.lbound()); 00338 assert(I.ubound() <= dim() + (TNT_BASE_OFFSET-1)); 00339 assert(I.lbound() <= I.ubound()); 00340 #endif 00341 return const_Region1D<Array1D>(A_, I.lbound()+offset_, 00342 offset_ + I.ubound()); 00343 } 00344 00345 00346 const T & operator() (Subscript i) const 00347 { 00348 #ifdef TNT_BOUNDS_CHECK 00349 assert(TNT_BASE_OFFSET <= i); 00350 assert(i <= dim() + (TNT_BASE_OFFSET-1)); 00351 #endif 00352 return A_(i+offset_); 00353 } 00354 00355 00356 00357 00358 }; 00359 00360 template <class Array1D> 00361 std::ostream& operator<<(std::ostream &s, const_Region1D<Array1D> &A) 00362 { 00363 Subscript N=A.dim(); 00364 00365 for (Subscript i=1; i<=N; i++) 00366 s << A(i) << endl; 00367 00368 return s; 00369 } 00370 00371 00372 } // namespace TNT 00373 00374 #endif // const_Region1D_H 00375