dune-localfunctions
2.2.0
|
00001 // -*- tab-width: 8; indent-tabs-mode: nil -*- 00002 // vi: set ts=8 sw=2 et sts=2: 00003 #ifndef DUNE_VIRTUALINTERFACE_HH 00004 #define DUNE_VIRTUALINTERFACE_HH 00005 00006 #include<dune/common/function.hh> 00007 00008 #include<dune/geometry/type.hh> 00009 00010 #include<dune/localfunctions/common/localbasis.hh> 00011 #include<dune/localfunctions/common/localkey.hh> 00012 #include<dune/localfunctions/common/localfiniteelementtraits.hh> 00013 00014 namespace Dune 00015 { 00016 00017 // forward declaration needed by the helper traits 00018 template<class DomainType, class RangeType> 00019 class LocalInterpolationVirtualInterface; 00020 00021 template<class T> 00022 class LocalBasisVirtualInterface; 00023 00024 // ----------------------------------------------------------------- 00025 // Helper traits classes 00026 // ----------------------------------------------------------------- 00027 00033 template<class T> 00034 struct LowerOrderLocalBasisTraits 00035 { 00037 typedef LocalBasisTraits< 00038 typename T::DomainFieldType, 00039 T::dimDomain, 00040 typename T::DomainType, 00041 typename T::RangeFieldType, 00042 T::dimRange, 00043 typename T::RangeType, 00044 typename T::JacobianType, 00045 T::diffOrder-1> Traits; 00046 }; 00047 00054 template<class T, int order> 00055 struct FixedOrderLocalBasisTraits 00056 { 00058 typedef LocalBasisTraits< 00059 typename T::DomainFieldType, 00060 T::dimDomain, 00061 typename T::DomainType, 00062 typename T::RangeFieldType, 00063 T::dimRange, 00064 typename T::RangeType, 00065 typename T::JacobianType, 00066 order> Traits; 00067 }; 00068 00074 template<class FE> 00075 class LocalFiniteElementFunctionBase 00076 { 00077 typedef typename FE::Traits::LocalBasisType::Traits::DomainType DomainType; 00078 typedef typename FE::Traits::LocalBasisType::Traits::RangeType RangeType; 00079 00080 typedef LocalInterpolationVirtualInterface<DomainType, RangeType> Interface; 00081 typedef typename FE::Traits::LocalInterpolationType Implementation; 00082 00083 public: 00084 00085 typedef VirtualFunction<DomainType, RangeType> VirtualFunctionBase; 00086 typedef Function<const DomainType&, RangeType&> FunctionBase; 00087 00093 typedef typename SelectType<IsBaseOf<Interface, Implementation>::value, VirtualFunctionBase, FunctionBase>::Type type; 00094 }; 00095 00096 00097 00098 // ----------------------------------------------------------------- 00099 // Basis 00100 // ----------------------------------------------------------------- 00101 00102 // current versions of doxygen (<= 1.6.2) enter an infinite loop when parsing 00103 // the following class 00104 #ifndef DOXYGEN 00105 00119 template<class T> 00120 class LocalBasisVirtualInterfaceBase : 00121 public virtual LocalBasisVirtualInterface<typename LowerOrderLocalBasisTraits<T>::Traits> 00122 { 00123 typedef LocalBasisVirtualInterface<typename LowerOrderLocalBasisTraits<T>::Traits> BaseInterface; 00124 public: 00125 typedef T Traits; 00126 00128 virtual void evaluate ( 00129 const typename Dune::template array<int,Traits::diffOrder>& directions, 00130 const typename Traits::DomainType& in, 00131 std::vector<typename Traits::RangeType>& out) const = 0; 00132 00133 using BaseInterface::evaluate; 00134 }; 00135 #endif // DOXYGEN 00136 00143 template<class DF, int n, class D, class RF, int m, class R, class J> 00144 class LocalBasisVirtualInterfaceBase<LocalBasisTraits<DF,n,D,RF,m,R,J,0> > 00145 { 00146 public: 00147 typedef LocalBasisTraits<DF,n,D,RF,m,R,J,0> Traits; 00148 00149 virtual ~LocalBasisVirtualInterfaceBase() {} 00150 00152 virtual unsigned int size () const = 0; 00153 00155 virtual unsigned int order () const = 0; 00156 00162 virtual void evaluateFunction (const typename Traits::DomainType& in, 00163 std::vector<typename Traits::RangeType>& out) const = 0; 00164 00173 virtual void evaluateJacobian(const typename Traits::DomainType& in, // position 00174 std::vector<typename Traits::JacobianType>& out) const = 0; 00175 00177 virtual void evaluate ( 00178 const typename Dune::template array<int,Traits::diffOrder>& directions, 00179 const typename Traits::DomainType& in, 00180 std::vector<typename Traits::RangeType>& out) const = 0; 00181 00182 }; 00183 00193 template<class T> 00194 class LocalBasisVirtualInterface : 00195 public virtual LocalBasisVirtualInterfaceBase<T> 00196 { 00197 typedef LocalBasisVirtualInterfaceBase<T> BaseInterface; 00198 public: 00199 typedef T Traits; 00200 00202 template <int k> 00203 void evaluate ( 00204 const typename Dune::template array<int,k>& directions, 00205 const typename Traits::DomainType& in, 00206 std::vector<typename Traits::RangeType>& out) const 00207 { 00208 typedef LocalBasisVirtualInterfaceBase<typename FixedOrderLocalBasisTraits<T,k>::Traits > OrderKBaseInterface; 00209 const OrderKBaseInterface& asBase = *this; 00210 asBase.evaluate(directions, in, out); 00211 } 00212 00213 using BaseInterface::size; 00214 using BaseInterface::order; 00215 using BaseInterface::evaluateFunction; 00216 using BaseInterface::evaluateJacobian; 00217 /* Unfortunately, the intel compiler cannot use the different evaluate 00218 * methods with varying argument lists. :-( */ 00219 #ifndef __INTEL_COMPILER 00220 using BaseInterface::evaluate; 00221 #endif 00222 }; 00223 00224 00225 00226 00227 // ----------------------------------------------------------------- 00228 // Interpolation 00229 // ----------------------------------------------------------------- 00230 00243 template<class DomainType, class RangeType> 00244 class LocalInterpolationVirtualInterfaceBase 00245 { 00246 public: 00247 00249 typedef Dune::VirtualFunction<DomainType, RangeType> FunctionType; 00250 00252 typedef typename RangeType::field_type CoefficientType; 00253 00254 virtual ~LocalInterpolationVirtualInterfaceBase() {} 00255 00263 virtual void interpolate (const FunctionType& f, std::vector<CoefficientType>& out) const = 0; 00264 }; 00265 00273 template<class DomainType, class RangeType> 00274 class LocalInterpolationVirtualInterface 00275 : public LocalInterpolationVirtualInterfaceBase<DomainType, RangeType> 00276 { 00277 public: 00278 00280 typedef Dune::VirtualFunction<DomainType, RangeType> FunctionType; 00281 00283 typedef typename RangeType::field_type CoefficientType; 00284 00285 00286 virtual ~LocalInterpolationVirtualInterface() {} 00287 00288 // This method is only notet again for to make the documentation complete. 00289 00297 virtual void interpolate (const FunctionType& f, std::vector<CoefficientType>& out) const = 0; 00298 00301 template<class F> 00302 void interpolate (const F& f, std::vector<CoefficientType>& out) const 00303 { 00304 const LocalInterpolationVirtualInterfaceBase<DomainType, RangeType>& asBase = *this; 00305 asBase.interpolate(VirtualFunctionWrapper<F>(f),out); 00306 } 00307 00308 template<class F, class C> 00309 void interpolate (const F& f, std::vector<C>& out) const 00310 { 00311 std::vector<CoefficientType> outDummy; 00312 const LocalInterpolationVirtualInterfaceBase<DomainType, RangeType>& asBase = *this; 00313 asBase.interpolate(VirtualFunctionWrapper<F>(f),outDummy); 00314 out.resize(outDummy.size()); 00315 for(typename std::vector<CoefficientType>::size_type i=0; i<outDummy.size(); ++i) 00316 out[i] = outDummy[i]; 00317 } 00318 00319 private: 00320 00321 template <typename F> 00322 struct VirtualFunctionWrapper 00323 : public FunctionType 00324 { 00325 public: 00326 VirtualFunctionWrapper(const F &f) 00327 : f_(f) 00328 {} 00329 00330 virtual ~VirtualFunctionWrapper() {} 00331 00332 virtual void evaluate(const DomainType& x, RangeType& y) const 00333 { 00334 f_.evaluate(x,y); 00335 } 00336 00337 const F &f_; 00338 }; 00339 }; 00340 00341 00342 00343 // ----------------------------------------------------------------- 00344 // Coefficients 00345 // ----------------------------------------------------------------- 00346 00352 class LocalCoefficientsVirtualInterface 00353 { 00354 public: 00355 00356 virtual ~LocalCoefficientsVirtualInterface() {} 00357 00359 virtual std::size_t size () const = 0; 00360 00362 const virtual LocalKey& localKey (std::size_t i) const = 0; 00363 00364 }; 00365 00366 00367 00368 // ----------------------------------------------------------------- 00369 // Finite Element 00370 // ----------------------------------------------------------------- 00371 00378 template<class T> 00379 class LocalFiniteElementVirtualInterface 00380 : public virtual LocalFiniteElementVirtualInterface<typename LowerOrderLocalBasisTraits<T>::Traits > 00381 { 00382 typedef LocalFiniteElementVirtualInterface<typename LowerOrderLocalBasisTraits<T>::Traits > BaseInterface; 00383 00384 public: 00385 typedef LocalFiniteElementTraits< 00386 LocalBasisVirtualInterface<T>, 00387 LocalCoefficientsVirtualInterface, 00388 LocalInterpolationVirtualInterface< 00389 typename T::DomainType, 00390 typename T::RangeType> > Traits; 00391 00393 virtual const typename Traits::LocalBasisType& localBasis () const = 0; 00394 00395 using BaseInterface::localBasis; 00396 using BaseInterface::localCoefficients; 00397 using BaseInterface::localInterpolation; 00398 using BaseInterface::type; 00399 00400 virtual LocalFiniteElementVirtualInterface<T>* clone() const = 0; 00401 }; 00402 00403 00410 template<class DF, int n, class D, class RF, int m, class R, class J> 00411 class LocalFiniteElementVirtualInterface<LocalBasisTraits<DF,n,D,RF,m,R,J,0> > 00412 { 00413 typedef LocalBasisTraits<DF,n,D,RF,m,R,J,0> T; 00414 00415 public: 00416 typedef LocalFiniteElementTraits< 00417 LocalBasisVirtualInterface<T>, 00418 LocalCoefficientsVirtualInterface, 00419 LocalInterpolationVirtualInterface< 00420 typename T::DomainType, 00421 typename T::RangeType> > Traits; 00422 00423 virtual ~LocalFiniteElementVirtualInterface() {} 00424 00426 virtual const typename Traits::LocalBasisType& localBasis () const = 0; 00427 00429 virtual const typename Traits::LocalCoefficientsType& localCoefficients () const = 0; 00430 00432 virtual const typename Traits::LocalInterpolationType& localInterpolation () const = 0; 00433 00435 virtual const GeometryType type () const = 0; 00436 00437 virtual LocalFiniteElementVirtualInterface<T>* clone() const = 0; 00438 }; 00439 00440 } 00441 #endif