|
Intrepid
|
00001 // @HEADER 00002 // ************************************************************************ 00003 // 00004 // Intrepid Package 00005 // Copyright (2007) Sandia Corporation 00006 // 00007 // Under terms of Contract DE-AC04-94AL85000, there is a non-exclusive 00008 // license for use of this work by or on behalf of the U.S. Government. 00009 // 00010 // Redistribution and use in source and binary forms, with or without 00011 // modification, are permitted provided that the following conditions are 00012 // met: 00013 // 00014 // 1. Redistributions of source code must retain the above copyright 00015 // notice, this list of conditions and the following disclaimer. 00016 // 00017 // 2. Redistributions in binary form must reproduce the above copyright 00018 // notice, this list of conditions and the following disclaimer in the 00019 // documentation and/or other materials provided with the distribution. 00020 // 00021 // 3. Neither the name of the Corporation nor the names of the 00022 // contributors may be used to endorse or promote products derived from 00023 // this software without specific prior written permission. 00024 // 00025 // THIS SOFTWARE IS PROVIDED BY SANDIA CORPORATION "AS IS" AND ANY 00026 // EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 00027 // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 00028 // PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL SANDIA CORPORATION OR THE 00029 // CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, 00030 // EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 00031 // PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 00032 // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF 00033 // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 00034 // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 00035 // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 00036 // 00037 // Questions: Alejandro Mota (amota@sandia.gov) 00038 // 00039 // ************************************************************************ 00040 // @HEADER 00041 00042 #if !defined(Intrepid_MiniTensor_Storage_h) 00043 #define Intrepid_MiniTensor_Storage_h 00044 00045 #include "Intrepid_MiniTensor_Definitions.h" 00046 00047 namespace Intrepid { 00048 00050 template <Index N, Index C> 00051 struct dimension_const { 00052 static Index const value = C; 00053 }; 00054 00055 template <Index C> 00056 struct dimension_const<DYNAMIC, C> { 00057 static Index const value = DYNAMIC; 00058 }; 00059 00061 template <Index D> 00062 struct check_static { 00063 static Index const 00064 maximum_dimension = static_cast<Index>(std::numeric_limits<Index>::digits); 00065 00066 STATIC_ASSERT(D < maximum_dimension, dimension_too_large); 00067 static Index const value = D; 00068 }; 00069 00070 template <typename Store> 00071 inline 00072 void 00073 check_dynamic(Index const dimension) 00074 { 00075 Index const 00076 maximum_dimension = static_cast<Index>(std::numeric_limits<Index>::digits); 00077 00078 assert(Store::IS_DYNAMIC == true); 00079 00080 if (dimension > maximum_dimension) { 00081 std::cerr << "ERROR: " << __PRETTY_FUNCTION__; 00082 std::cerr << std::endl; 00083 std::cerr << "Requested dimension (" << dimension; 00084 std::cerr << ") exceeds maximum allowed: " << maximum_dimension; 00085 std::cerr << std::endl; 00086 exit(1); 00087 } 00088 } 00089 00091 template <Index D, Index O> 00092 struct dimension_power { 00093 static Index const value = 0; 00094 }; 00095 00096 template <Index D> 00097 struct dimension_power<D, 1> { 00098 static Index const value = D; 00099 }; 00100 00101 template <Index D> 00102 struct dimension_power<D, 2> { 00103 static Index const value = D * D; 00104 }; 00105 00106 template <Index D> 00107 struct dimension_power<D, 3> { 00108 static Index const value = D * D * D; 00109 }; 00110 00111 template <Index D> 00112 struct dimension_power<D, 4> { 00113 static Index const value = D * D * D * D; 00114 }; 00115 00117 template <Index N> 00118 struct dimension_square { 00119 static Index const value = 0; 00120 }; 00121 00122 template <> 00123 struct dimension_square<DYNAMIC> { 00124 static Index const value = DYNAMIC; 00125 }; 00126 00127 template <> 00128 struct dimension_square<1> { 00129 static Index const value = 1; 00130 }; 00131 00132 template <> 00133 struct dimension_square<2> { 00134 static Index const value = 4; 00135 }; 00136 00137 template <> 00138 struct dimension_square<3> { 00139 static Index const value = 9; 00140 }; 00141 00142 template <> 00143 struct dimension_square<4> { 00144 static Index const value = 16; 00145 }; 00146 00150 template <Index N> 00151 struct dimension_sqrt { 00152 static Index const value = 0; 00153 }; 00154 00155 template <> 00156 struct dimension_sqrt<DYNAMIC> { 00157 static Index const value = DYNAMIC; 00158 }; 00159 00160 template <> 00161 struct dimension_sqrt<1> { 00162 static Index const value = 1; 00163 }; 00164 00165 template <> 00166 struct dimension_sqrt<4> { 00167 static Index const value = 2; 00168 }; 00169 00170 template <> 00171 struct dimension_sqrt<9> { 00172 static Index const value = 3; 00173 }; 00174 00175 template <> 00176 struct dimension_sqrt<16> { 00177 static Index const value = 4; 00178 }; 00179 00181 template <Index N, Index P> 00182 struct dimension_add { 00183 static Index const value = N + P; 00184 }; 00185 00186 template <Index P> 00187 struct dimension_add<DYNAMIC, P> { 00188 static Index const value = DYNAMIC; 00189 }; 00190 00191 template <Index N, Index P> 00192 struct dimension_subtract { 00193 static Index const value = N - P; 00194 }; 00195 00196 template <Index P> 00197 struct dimension_subtract<DYNAMIC, P> { 00198 static Index const value = DYNAMIC; 00199 }; 00200 00204 template<typename T, Index N> 00205 class Storage 00206 { 00207 public: 00208 typedef T value_type; 00209 typedef T * pointer_type; 00210 typedef T & reference_type; 00211 typedef T const * const_pointer_type; 00212 typedef T const & const_reference_type; 00213 00214 static 00215 bool const 00216 IS_STATIC = true; 00217 00218 static 00219 bool const 00220 IS_DYNAMIC = false; 00221 00222 Storage() {} 00223 00224 explicit 00225 Storage(Index const number_entries) {resize(number_entries);} 00226 00227 ~Storage() {} 00228 00229 T const & 00230 operator[](Index const i) const 00231 {assert(i < N); return storage_[i];} 00232 00233 T & 00234 operator[](Index const i) 00235 {assert(i < N); return storage_[i];} 00236 00237 Index 00238 size() const {return N;} 00239 00240 void 00241 resize(Index const number_entries) {assert(number_entries == N);} 00242 00243 void 00244 clear() {} 00245 00246 pointer_type 00247 get_pointer() {return &storage_[0];} 00248 00249 const_pointer_type 00250 get_const_pointer() const {return &storage_[0];} 00251 00252 private: 00253 00254 Storage(Storage<T, N> const & s); 00255 00256 Storage<T, N> & 00257 operator=(Storage<T, N> const & s); 00258 00259 T 00260 storage_[N]; 00261 00262 }; 00263 00267 template<typename T> 00268 class Storage<T, DYNAMIC> 00269 { 00270 public: 00271 typedef T value_type; 00272 typedef T * pointer_type; 00273 typedef T & reference_type; 00274 typedef T const * const_pointer_type; 00275 typedef T const & const_reference_type; 00276 00277 static 00278 bool const 00279 IS_DYNAMIC = true; 00280 00281 static 00282 bool const 00283 IS_STATIC = false; 00284 00285 Storage() : storage_(NULL), size_(0) {} 00286 00287 explicit 00288 Storage(Index const number_entries) : storage_(NULL), size_(0) 00289 {resize(number_entries);} 00290 00291 ~Storage() {clear();} 00292 00293 T const & 00294 operator[](Index const i) const 00295 {assert(i < size()); return storage_[i];} 00296 00297 T & 00298 operator[](Index const i) 00299 {assert(i < size()); return storage_[i];} 00300 00301 Index 00302 size() const 00303 {return size_;} 00304 00305 void 00306 resize(Index const number_entries) 00307 { 00308 if (number_entries != size_) { 00309 clear(); storage_ = new T[number_entries]; size_ = number_entries; 00310 } 00311 } 00312 00313 void 00314 clear() 00315 { 00316 if (storage_ != NULL) { 00317 delete [] storage_; storage_ = NULL; size_ = 0; 00318 } 00319 } 00320 00321 pointer_type 00322 get_pointer() {return storage_;} 00323 00324 const_pointer_type 00325 get_const_pointer() const {return storage_;} 00326 00327 private: 00328 00329 Storage(Storage<T, DYNAMIC> const & s); 00330 00331 Storage<T, DYNAMIC> & 00332 operator=(Storage<T, DYNAMIC> const & s); 00333 00334 T * 00335 storage_; 00336 00337 Index 00338 size_; 00339 }; 00340 00341 } // namespace Intrepid 00342 00343 #include "Intrepid_MiniTensor_Storage.i.h" 00344 00345 #endif // Intrepid_MiniTensor_Storage_h
1.7.6.1