Dune Core Modules (2.7.1)

l2interpolation.hh
1 // -*- tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 2 -*-
2 // vi: set et ts=4 sw=2 sts=2:
3 #ifndef DUNE_L2INTERPOLATION_HH
4 #define DUNE_L2INTERPOLATION_HH
5 
6 #include <dune/common/concept.hh>
7 
9 
10 #include <dune/localfunctions/common/localinterpolation.hh>
11 #include <dune/localfunctions/utility/lfematrix.hh>
12 
13 namespace Dune
14 {
30  template< class B, class Q, bool onb >
32 
33  template< class B, class Q >
34  class LocalL2InterpolationBase
35  {
36  typedef LocalL2InterpolationBase< B, Q > This;
37 
38  public:
39  typedef B Basis;
40  typedef Q Quadrature;
41 
42  static const unsigned int dimension = Basis::dimension;
43 
45  template< class Function, class DofField, std::enable_if_t<models<Impl::FunctionWithEvaluate<typename Function::DomainType, typename Function::RangeType>, Function>(), int> = 0 >
46  void interpolate ( const Function &function, std::vector< DofField > &coefficients ) const
47  {
48  typedef typename Quadrature::iterator Iterator;
49  typedef FieldVector< DofField, Basis::dimRange > RangeVector;
50 
51  const unsigned int size = basis().size();
52  static std::vector< RangeVector > basisValues( size );
53 
54  coefficients.resize( size );
55  basisValues.resize( size );
56  for( unsigned int i = 0; i < size; ++i )
57  coefficients[ i ] = Zero< DofField >();
58 
59  const Iterator end = quadrature().end();
60  for( Iterator it = quadrature().begin(); it != end; ++it )
61  {
62  basis().evaluate( it->position(), basisValues );
63  typename Function::RangeType val;
64  function.evaluate( field_cast<typename Function::DomainType::field_type>(it->position()), val );
65  RangeVector factor = field_cast< DofField >( val );
66  factor *= field_cast< DofField >( it->weight() );
67  for( unsigned int i = 0; i < size; ++i )
68  coefficients[ i ] += factor * basisValues[ i ];
69  }
70  }
71 
73  template< class Function, class DofField, std::enable_if_t<models<Impl::FunctionWithCallOperator<typename Quadrature::value_type::Vector>, Function>(), int> = 0 >
74  void interpolate ( const Function &function, std::vector< DofField > &coefficients ) const
75  {
76  typedef FieldVector< DofField, Basis::dimRange > RangeVector;
77 
78  const unsigned int size = basis().size();
79  static std::vector< RangeVector > basisValues( size );
80 
81  coefficients.resize( size );
82  basisValues.resize( size );
83  for( unsigned int i = 0; i < size; ++i )
84  coefficients[ i ] = Zero< DofField >();
85 
86  for (auto&& qp : quadrature())
87  {
88  basis().evaluate( qp.position(), basisValues );
89  auto val = function( qp.position() );
90  RangeVector factor = field_cast< DofField >( val );
91  factor *= field_cast< DofField >( qp.weight() );
92  for( unsigned int i = 0; i < size; ++i )
93  coefficients[ i ] += factor * basisValues[ i ];
94  }
95  }
96 
97  const Basis &basis () const
98  {
99  return basis_;
100  }
101 
102  const Quadrature &quadrature () const
103  {
104  return quadrature_;
105  }
106 
107  protected:
108  LocalL2InterpolationBase ( const Basis &basis, const Quadrature &quadrature )
109  : basis_( basis ),
110  quadrature_( quadrature )
111  {}
112 
113  const Basis &basis_;
114  const Quadrature &quadrature_;
115  };
116 
117  template< class B, class Q >
118  struct LocalL2Interpolation<B,Q,true>
119  : public LocalL2InterpolationBase<B,Q>
120  {
121  typedef LocalL2InterpolationBase<B,Q> Base;
122  template< class BasisFactory, bool onb >
123  friend class LocalL2InterpolationFactory;
124  using typename Base::Basis;
125  using typename Base::Quadrature;
126  private:
127  LocalL2Interpolation ( const typename Base::Basis &basis, const typename Base::Quadrature &quadrature )
128  : Base(basis,quadrature)
129  {}
130  };
131  template< class B, class Q >
132  struct LocalL2Interpolation<B,Q,false>
133  : public LocalL2InterpolationBase<B,Q>
134  {
135  typedef LocalL2InterpolationBase<B,Q> Base;
136  template< class BasisFactory, bool onb >
137  friend class LocalL2InterpolationFactory;
138  using typename Base::Basis;
139  using typename Base::Quadrature;
140  template< class Function, class DofField >
141  void interpolate ( const Function &function, std::vector< DofField > &coefficients ) const
142  {
143  const unsigned size = Base::basis().size();
144  Base::interpolate(function,val_);
145  coefficients.resize( size );
146  for (unsigned int i=0; i<size; ++i)
147  {
148  coefficients[i] = 0;
149  for (unsigned int j=0; j<size; ++j)
150  {
151  coefficients[i] += field_cast<DofField>(massMatrix_(i,j)*val_[j]);
152  }
153  }
154  }
155  private:
156  LocalL2Interpolation ( const typename Base::Basis &basis, const typename Base::Quadrature &quadrature )
157  : Base(basis,quadrature),
158  val_(basis.size()),
159  massMatrix_()
160  {
161  typedef FieldVector< Field, Base::Basis::dimRange > RangeVector;
162  typedef typename Base::Quadrature::iterator Iterator;
163  const unsigned size = basis.size();
164  std::vector< RangeVector > basisValues( size );
165 
166  massMatrix_.resize( size,size );
167  for (unsigned int i=0; i<size; ++i)
168  for (unsigned int j=0; j<size; ++j)
169  massMatrix_(i,j) = 0;
170  const Iterator end = Base::quadrature().end();
171  for( Iterator it = Base::quadrature().begin(); it != end; ++it )
172  {
173  Base::basis().evaluate( it->position(), basisValues );
174  for (unsigned int i=0; i<size; ++i)
175  for (unsigned int j=0; j<size; ++j)
176  massMatrix_(i,j) += (basisValues[i]*basisValues[j])*it->weight();
177  }
178  if ( !massMatrix_.invert() )
179  {
180  DUNE_THROW(MathError, "Mass matrix singular in LocalL2Interpolation");
181  }
182 
183  }
184  typedef typename Base::Basis::StorageField Field;
185  typedef FieldVector< Field, Base::Basis::dimRange > RangeVector;
186  typedef LFEMatrix<Field> MassMatrix;
187  mutable std::vector<Field> val_;
188  MassMatrix massMatrix_;
189  };
190 
195  template< class BasisFactory, bool onb >
197  {
198  static const unsigned int dimension = BasisFactory::dimension;
199  typedef typename BasisFactory::Key Key;
200  typedef typename BasisFactory::Object Basis;
201  typedef double Field;
205  typedef const LocalInterpolation Object;
206 
207  template< class Topology >
208  static Object *create ( const Key &key )
209  {
210  Dune::GeometryType gt(Topology::id, Topology::dimension);
211  const Basis *basis = BasisFactory::template create< Topology >( key );
212  const Quadrature & quadrature = QuadratureProvider::rule(gt, 2*basis->order()+1);
213  return new Object( *basis, quadrature );
214  }
215  static void release ( Object *object )
216  {
217  const Basis &basis = object->basis();
218  BasisFactory::release( &basis );
219  delete object;
220  }
221  };
222 
223 }
224 
225 #endif // #ifndef DUNE_L2INTERPOLATION_HH
vector space out of a tensor product of fields.
Definition: fvector.hh:96
Base class template for function classes.
Definition: function.hh:29
RawRangeType RangeType
Raw type of input variable with removed reference and constness.
Definition: function.hh:36
Unique label for each type of entities that can occur in DUNE grids.
Definition: type.hh:279
Abstract base class for quadrature rules.
Definition: quadraturerules.hh:126
A container for all quadrature rules of dimension dim
Definition: quadraturerules.hh:172
static const QuadratureRule & rule(const GeometryType &t, int p, QuadratureType::Enum qt=QuadratureType::GaussLegendre)
select the appropriate QuadratureRule for GeometryType t and order p
Definition: quadraturerules.hh:254
Infrastructure for concepts.
#define DUNE_THROW(E, m)
Definition: exceptions.hh:216
bool gt(const T &first, const T &second, typename EpsilonType< T >::Type epsilon)
test if first greater than second
Definition: float_cmp.cc:156
Dune namespace.
Definition: alignedallocator.hh:14
A factory class for the local l2 interpolations taking a basis factory.
Definition: l2interpolation.hh:197
A local L2 interpolation taking a test basis and a quadrature rule.
Definition: l2interpolation.hh:31
A class representing the zero of a given Field.
Definition: field.hh:77
Creative Commons License   |  Legal Statements / Impressum  |  Hosted by TU Dresden  |  generated with Hugo v0.80.0 (May 16, 22:29, 2024)