$extrastylesheet
00001 // The libMesh Finite Element Library. 00002 // Copyright (C) 2002-2014 Benjamin S. Kirk, John W. Peterson, Roy H. Stogner 00003 00004 // This library is free software; you can redistribute it and/or 00005 // modify it under the terms of the GNU Lesser General Public 00006 // License as published by the Free Software Foundation; either 00007 // version 2.1 of the License, or (at your option) any later version. 00008 00009 // This library is distributed in the hope that it will be useful, 00010 // but WITHOUT ANY WARRANTY; without even the implied warranty of 00011 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 00012 // Lesser General Public License for more details. 00013 00014 // You should have received a copy of the GNU Lesser General Public 00015 // License along with this library; if not, write to the Free Software 00016 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 00017 00018 00019 00020 #ifndef LIBMESH_RAW_ACCESSOR_H 00021 #define LIBMESH_RAW_ACCESSOR_H 00022 00023 // Local includes 00024 #include "libmesh/libmesh_common.h" 00025 00026 #include "libmesh/tensor_value.h" 00027 #include "libmesh/vector_value.h" 00028 #include "libmesh/type_n_tensor.h" 00029 00030 namespace libMesh 00031 { 00032 00036 template <typename FieldType> 00037 struct RawFieldType {}; 00038 00039 template <> 00040 struct RawFieldType<Number> 00041 { 00042 typedef Number type; 00043 }; 00044 00045 template <> 00046 struct RawFieldType<Gradient> 00047 { 00048 typedef Number type; 00049 }; 00050 00051 template <> 00052 struct RawFieldType<Tensor> 00053 { 00054 typedef Number type; 00055 }; 00056 00057 template<> 00058 struct RawFieldType<TypeNTensor<3, Number> > 00059 { 00060 typedef Number type; 00061 }; 00062 00063 #ifdef LIBMESH_USE_COMPLEX_NUMBERS 00064 template <> 00065 struct RawFieldType<Real> 00066 { 00067 typedef Real type; 00068 }; 00069 00070 template <> 00071 struct RawFieldType<RealGradient> 00072 { 00073 typedef Real type; 00074 }; 00075 00076 template <> 00077 struct RawFieldType<RealTensor> 00078 { 00079 typedef Real type; 00080 }; 00081 00082 template<> 00083 struct RawFieldType<TypeNTensor<3, Real> > 00084 { 00085 typedef Real type; 00086 }; 00087 #endif 00088 00092 template <typename FieldType> 00093 class RawAccessor 00094 { 00095 public: 00096 00097 RawAccessor( FieldType& data, const unsigned int dim ) 00098 : _data(data), 00099 _dim(dim) 00100 {} 00101 00102 ~RawAccessor(){} 00103 00104 typename RawFieldType<FieldType>::type& operator()( unsigned int i ); 00105 const typename RawFieldType<FieldType>::type& operator()( unsigned int i ) const; 00106 00107 private: 00108 RawAccessor(); 00109 00110 FieldType& _data; 00111 const unsigned int _dim; 00112 }; 00113 00114 // Specialize for specific cases 00115 template<> 00116 inline 00117 Number& RawAccessor<Number>::operator()( unsigned int libmesh_dbg_var(i) ) 00118 { 00119 libmesh_assert_equal_to (i, 0); 00120 return this->_data; 00121 } 00122 00123 template<> 00124 inline 00125 Number& RawAccessor<Gradient>::operator()( unsigned int i ) 00126 { 00127 libmesh_assert_less (i, this->_dim); 00128 return this->_data(i); 00129 } 00130 00131 template<> 00132 inline 00133 Number& RawAccessor<Tensor>::operator()( unsigned int k ) 00134 { 00135 libmesh_assert_less (k, this->_dim*this->_dim); 00136 00137 // For tensors, each row is filled first, i.e. for 2-D 00138 // [ 0 1; 2 3] 00139 // Thus, k(i,j) = j + i*dim 00140 unsigned int ii = k/_dim; 00141 unsigned int jj = k - ii*_dim; 00142 00143 return this->_data(ii,jj); 00144 } 00145 00149 template <unsigned int N, typename ScalarType> 00150 class RawAccessor<TypeNTensor<N, ScalarType> > 00151 { 00152 public: 00153 00154 typedef TypeNTensor<N, ScalarType> FieldType; 00155 00156 RawAccessor( FieldType& data, const unsigned int dim ) 00157 : _data(data), 00158 _dim(dim) 00159 {} 00160 00161 ~RawAccessor(){} 00162 00163 typename RawFieldType<FieldType>::type& operator()( unsigned int /*i*/ ) 00164 { return dummy; } 00165 00166 const typename RawFieldType<FieldType>::type& operator()( unsigned int /*i*/ ) const 00167 { return dummy; } 00168 00169 private: 00170 RawAccessor(); 00171 00172 ScalarType dummy; 00173 00174 FieldType& _data; 00175 const unsigned int _dim; 00176 }; 00177 00178 #ifdef LIBMESH_USE_COMPLEX_NUMBERS 00179 template<> 00180 inline 00181 Real& RawAccessor<Real>::operator()( unsigned int i ) 00182 { 00183 libmesh_assert_equal_to (i, 0); 00184 return this->_data; 00185 } 00186 00187 template<> 00188 inline 00189 Real& RawAccessor<RealGradient>::operator()( unsigned int i ) 00190 { 00191 libmesh_assert_less (i, this->_dim); 00192 return this->_data(i); 00193 } 00194 00195 template<> 00196 inline 00197 Real& RawAccessor<RealTensor>::operator()( unsigned int k ) 00198 { 00199 libmesh_assert_less (k, this->_dim*this->_dim); 00200 00201 // For tensors, each row is filled first, i.e. for 2-D 00202 // [ 0 1; 2 3] 00203 // Thus, k(i,j) = i + j*dim 00204 unsigned int jj = k/_dim; 00205 unsigned int ii = k - jj*_dim; 00206 00207 return this->_data(ii,jj); 00208 } 00209 00210 #endif 00211 00212 } 00213 #endif // LIBMESH_RAW_ACCESSOR_H