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