dune-localfunctions  2.1.1
localtoglobaladaptors.hh
Go to the documentation of this file.
00001 // -*- tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*-
00002 // vi: set et ts=8 sw=2 sts=2:
00003 
00004 #ifndef DUNE_LOCALFUNCTIONS_COMMON_LOCALTOGLOBALADAPTORS_HH
00005 #define DUNE_LOCALFUNCTIONS_COMMON_LOCALTOGLOBALADAPTORS_HH
00006 
00007 #include <cstddef>
00008 #include <vector>
00009 
00010 #include <dune/common/fmatrix.hh>
00011 #include <dune/common/fvector.hh>
00012 #include <dune/common/geometrytype.hh>
00013 #include <dune/common/static_assert.hh>
00014 #include <dune/common/typetraits.hh>
00015 
00016 namespace Dune {
00017 
00019 
00027   template<class LocalBasisTraits, std::size_t dimDomainGlobal_>
00028   struct LocalToGlobalBasisAdaptorTraits {
00029     typedef typename LocalBasisTraits::DomainFieldType DomainField;
00030     static const std::size_t dimDomainLocal = LocalBasisTraits::dimDomain;
00031     static const std::size_t dimDomainGlobal = dimDomainGlobal_;
00032     typedef typename LocalBasisTraits::DomainType DomainLocal;
00033     typedef FieldVector<DomainField, dimDomainGlobal> DomainGlobal;
00034 
00035     typedef typename LocalBasisTraits::RangeFieldType RangeField;
00036     static const std::size_t dimRange = LocalBasisTraits::dimRange;
00037     typedef typename LocalBasisTraits::RangeType Range;
00038 
00039     typedef FieldMatrix<RangeField, dimRange, dimDomainGlobal> Jacobian;
00040 
00041     static const std::size_t diffOrder = LocalBasisTraits::diffOrder;
00042   };
00043 
00045 
00064   template<class LocalBasis, class Geometry>
00065   class ScalarLocalToGlobalBasisAdaptor {
00066     dune_static_assert(LocalBasis::Traits::dimRange == 1,
00067                        "ScalarLocalToGlobalBasisAdaptor can only wrap a "
00068                        "scalar local basis.");
00069     dune_static_assert((is_same<typename LocalBasis::Traits::DomainFieldType,
00070                                 typename Geometry::ctype>::value),
00071                        "ScalarLocalToGlobalBasisAdaptor: LocalBasis must use "
00072                        "the same ctype as Geometry");
00073     dune_static_assert
00074       ( static_cast<std::size_t>(LocalBasis::Traits::dimDomain) ==
00075           static_cast<std::size_t>(Geometry::mydimension),
00076         "ScalarLocalToGlobalBasisAdaptor: LocalBasis domain dimension must "
00077         "match local dimension of Geometry");
00078 
00079     const LocalBasis& localBasis;
00080     const Geometry& geometry;
00081 
00082   public:
00083     typedef LocalToGlobalBasisAdaptorTraits<typename LocalBasis::Traits,
00084                                             Geometry::coorddimension> Traits;
00085 
00087 
00096     ScalarLocalToGlobalBasisAdaptor(const LocalBasis& localBasis_,
00097                                     const Geometry& geometry_) :
00098       localBasis(localBasis_), geometry(geometry_)
00099     { }
00100 
00101     std::size_t size() const { return localBasis.size(); }
00103 
00110     std::size_t order() const {
00111       if(geometry.affine())
00112         // affine linear
00113         return localBasis.order();
00114       else
00115         // assume at most order dim
00116         return localBasis.order() + Traits::dimDomainGlobal - 1;
00117     }
00118 
00119     void evaluateFunction(const typename Traits::DomainLocal& in,
00120                           std::vector<typename Traits::Range>& out) const
00121     {
00122       localBasis.evaluateFunction(in, out);
00123     }
00124 
00125     void evaluateJacobian(const typename Traits::DomainLocal& in,
00126                           std::vector<typename Traits::Jacobian>& out) const
00127     {
00128       std::vector<typename LocalBasis::Traits::JacobianType>
00129         localJacobian(size());
00130       localBasis.evaluateJacobian(in, localJacobian);
00131 
00132       const typename Geometry::Jacobian &geoJacobian =
00133         geometry.jacobianInverseTransposed(in);
00134 
00135       out.resize(size());
00136       for(std::size_t i = 0; i < size(); ++i)
00137         geoJacobian.mv(localJacobian[i][0], out[i][0]);
00138     }
00139   };
00140 
00142 
00148   template<class LocalInterpolation, class Traits_>
00149   class LocalToGlobalInterpolationAdaptor {
00150     const LocalInterpolation& localInterpolation;
00151 
00152   public:
00153     typedef Traits_ Traits;
00154 
00156 
00164     LocalToGlobalInterpolationAdaptor
00165     ( const LocalInterpolation& localInterpolation_) :
00166       localInterpolation(localInterpolation_)
00167     { }
00168 
00169     template<class Function, class Coeff>
00170     void interpolate(const Function& function, std::vector<Coeff>& out) const
00171     { localInterpolation.interpolate(function, out); }
00172   };
00173 
00176 
00186   template<class LocalFiniteElement, class Geometry>
00187   struct ScalarLocalToGlobalFiniteElementAdaptor {
00191     struct Traits {
00192       typedef ScalarLocalToGlobalBasisAdaptor<typename LocalFiniteElement::
00193               Traits::LocalBasisType, Geometry> Basis;
00194       typedef LocalToGlobalInterpolationAdaptor<typename LocalFiniteElement::
00195               Traits::LocalInterpolationType, typename Basis::Traits>
00196               Interpolation;
00197       typedef typename LocalFiniteElement::Traits::LocalCoefficientsType
00198               Coefficients;
00199     };
00200 
00201   private:
00202     const LocalFiniteElement &localFE;
00203     typename Traits::Basis basis_;
00204     typename Traits::Interpolation interpolation_;
00205 
00206   public:
00208 
00217     ScalarLocalToGlobalFiniteElementAdaptor
00218     ( const LocalFiniteElement& localFE_, const Geometry &geometry) :
00219       localFE(localFE_),
00220       basis_(localFE.localBasis(), geometry),
00221       interpolation_(localFE.localInterpolation())
00222     { }
00223 
00224     const typename Traits::Basis& basis() const { return basis_; }
00225     const typename Traits::Interpolation& interpolation() const
00226     { return interpolation_; }
00227     const typename Traits::Coefficients& coefficients() const
00228     { return localFE.localCoefficients(); }
00229     GeometryType type() const { return localFE.type(); }
00230   };
00231 
00233 
00243   template<class LocalFiniteElement, class Geometry>
00244   class ScalarLocalToGlobalFiniteElementAdaptorFactory {
00245     const LocalFiniteElement& localFE;
00246 
00247   public:
00248     typedef ScalarLocalToGlobalFiniteElementAdaptor<LocalFiniteElement,
00249                                                     Geometry> FiniteElement;
00250 
00252 
00260     ScalarLocalToGlobalFiniteElementAdaptorFactory
00261     (const LocalFiniteElement &localFE_) : localFE(localFE_) {}
00262 
00264 
00274     const FiniteElement make(const Geometry& geometry) {
00275       return FiniteElement(localFE, geometry);
00276     }
00277   };
00278 
00279 } // namespace Dune
00280 
00281 #endif // DUNE_LOCALFUNCTIONS_COMMON_LOCALTOGLOBALADAPTORS_HH