dune-fem 2.8.0
Loading...
Searching...
No Matches
space/shapefunctionset/tuple.hh
Go to the documentation of this file.
1#ifndef DUNE_FEM_SPACE_SHAPEFUNCTIONSET_TUPLE_HH
2#define DUNE_FEM_SPACE_SHAPEFUNCTIONSET_TUPLE_HH
3
4#include <tuple>
5
6#include <dune/geometry/type.hh>
7
9#include <dune/common/tupleutility.hh>
11
13
14
15namespace Dune
16{
17
18 namespace Fem
19 {
20
21 // TupleShapeFunctionSet
22 // ---------------------
23
24 template< class ... ShapeFunctionSets >
26 {
28
29 template< int ... I >
30 struct RangeOffsets
31 {
32 typedef std::tuple< std::integral_constant< int, I > ... > RangeSizeTuple;
33
34 template< int j >
35 static constexpr int size () { return std::tuple_element< j, RangeSizeTuple >::type::value; }
36
37 template< int ... j >
38 static constexpr std::integer_sequence< int, size< j >() ... > sizes ( std::integer_sequence< int, j ... > )
39 {
40 return std::integer_sequence< int, size< j >() ... >();
41 }
42
43 template< int i >
44 static constexpr int offset ()
45 {
46 return sum( sizes( std::make_integer_sequence< int, i >() ) );
47 }
48
49 private:
50 template< int ... j >
51 static constexpr int sum ( std::integer_sequence< int, j ... > )
52 {
53 return Std::sum( j ... );
54 }
55
56 static constexpr int sum ( std::integer_sequence< int > ) { return 0; }
57 };
58
59 typedef std::array< std::size_t, sizeof ... ( ShapeFunctionSets ) +1 > Offset;
60
61 template< int I > struct Offsets;
62 template< class Functor, class Value, int I > struct FunctorWrapper;
63
64 template< int I > struct EvaluateEach;
65 template< int I > struct JacobianEach;
66 template< int I > struct HessianEach;
67
68 static const std::size_t dimRange = Std::sum( static_cast< int >( ShapeFunctionSets::FunctionSpaceType::dimRange ) ... );
69
70 public:
71 template< std::size_t i >
72 using SubShapeFunctionSetType = std::tuple_element_t< i, std::tuple< ShapeFunctionSets... > >;
73
75
76 typedef typename FunctionSpaceType::DomainType DomainType;
77 typedef typename FunctionSpaceType::RangeType RangeType;
78 typedef typename FunctionSpaceType::JacobianRangeType JacobianRangeType;
79 typedef typename FunctionSpaceType::HessianRangeType HessianRangeType;
80
82 }
83
84 TupleShapeFunctionSet ( GeometryType type )
85 : shapeFunctionSetTuple_( makeGeometryTypeTuple( type, std::index_sequence_for< ShapeFunctionSets ... >() ) )
86 {
87 offset_[ 0 ] = 0;
88 Fem::ForLoop< Offsets, 0, sizeof ... ( ShapeFunctionSets ) -1 >::apply( shapeFunctionSetTuple_, offset_ );
89 }
90
91 template< class ... Args >
92 TupleShapeFunctionSet ( Args && ... args )
93 : shapeFunctionSetTuple_( std::forward< Args >( args ) ... )
94 {
95 offset_[ 0 ] = 0;
96 Fem::ForLoop< Offsets, 0, sizeof ... ( ShapeFunctionSets ) -1 >::apply( shapeFunctionSetTuple_, offset_ );
97 }
98
99 explicit TupleShapeFunctionSet ( const std::tuple< ShapeFunctionSets... > &shapeFunctionSetTuple )
100 : shapeFunctionSetTuple_( shapeFunctionSetTuple )
101 {
102 offset_[ 0 ] = 0;
103 Fem::ForLoop< Offsets, 0, sizeof ... ( ShapeFunctionSets ) -1 >::apply( shapeFunctionSetTuple_, offset_ );
104 }
105
106 int order () const { return order( std::index_sequence_for< ShapeFunctionSets ... >() ); }
107
108 std::size_t size () const { return size( std::index_sequence_for< ShapeFunctionSets ... >() ); }
109
110 template< class Point, class Functor >
111 void evaluateEach ( const Point &x, Functor functor ) const
112 {
113 Fem::ForLoop< EvaluateEach, 0, sizeof ... ( ShapeFunctionSets ) -1 >::apply( shapeFunctionSetTuple_, offset_, x, functor );
114 }
115
116 template< class Point, class Functor >
117 void jacobianEach ( const Point &x, Functor functor ) const
118 {
119 Fem::ForLoop< JacobianEach, 0, sizeof ... ( ShapeFunctionSets ) -1 >::apply( shapeFunctionSetTuple_, offset_, x, functor );
120 }
121
122 template< class Point, class Functor >
123 void hessianEach ( const Point &x, Functor functor ) const
124 {
125 Fem::ForLoop< HessianEach, 0, sizeof ... ( ShapeFunctionSets ) -1 >::apply( shapeFunctionSetTuple_, offset_, x, functor );
126 }
127
128 template< std::size_t i >
129 const SubShapeFunctionSetType< i > &subShapeFunctionSet ( std::integral_constant< std::size_t, i > = {} ) const
130 {
131 return std::get< i >( shapeFunctionSetTuple_ );
132 }
133
134 protected:
135 template< std::size_t ... I >
136 int order ( std::index_sequence< I ... > ) const
137 {
138 return Std::max( std::get< I >( shapeFunctionSetTuple_ ).order() ... );
139 }
140
141 template< std::size_t ... I >
142 std::size_t size ( std::index_sequence< I ... > ) const
143 {
144 return Std::sum( std::get< I >( shapeFunctionSetTuple_ ).size() ... );
145 }
146
147 template< int >
148 static GeometryType makeGeometryType ( GeometryType type )
149 {
150 return type;
151 }
152
153 template< std::size_t ... I >
154 static std::tuple< decltype( makeGeometryType< I >( std::declval< GeometryType >() ) ) ... >
155 makeGeometryTypeTuple ( GeometryType type, std::index_sequence< I ... > )
156 {
157 return std::make_tuple( makeGeometryType< I >( type ) ... );
158 }
159
161 Offset offset_;
162 };
163
164
165
166 // TupleShapeFunctionSet::Offsets
167 // ------------------------------
168
169 template< class ... ShapeFunctionSets >
170 template< int I >
171 struct TupleShapeFunctionSet< ShapeFunctionSets ... >::Offsets
172 {
173 template< class Tuple >
174 static void apply ( const Tuple &tuple, Offset &offset )
175 {
176 offset[ I + 1 ] = offset[ I ] + std::get< I >( tuple ).size();
177 }
178 };
179
180
181
182 // TupleShapeFunctionSet::FunctorWrapper
183 // -------------------------------------
184
185 template< class ... ShapeFunctionSets >
186 template< class Functor, class Value, int I >
187 struct TupleShapeFunctionSet< ShapeFunctionSets ... >::FunctorWrapper
188 {
189 static const int rangeOffset = RangeOffsets< ShapeFunctionSets::FunctionSpaceType::dimRange ... >::template offset< I >();
190
191 explicit FunctorWrapper ( const Functor &functor, const Offset &offset )
192 : functor_( functor ), offset_( offset ) {}
193
194 template< class Scalar >
195 void operator() ( const std::size_t i, const Scalar &subValue )
196 {
197 Value value( typename FieldTraits< Value >::field_type( 0.0 ) );
198 std::copy( subValue.begin(), subValue.end(), value.begin() + rangeOffset );
199 functor_( offset_[ I ] + i, value );
200 }
201
202 template< class K >
203 void operator () ( const std::size_t i, const Dune::FieldVector< K, 1 > &subValue )
204 {
205 MakeVectorialExpression< Dune::FieldVector< K, 1 >, Value > value( rangeOffset, subValue[ 0 ] );
206 functor_( offset_[ I ] + i, value );
207 }
208
209 template< class K, int n >
210 void operator () ( const std::size_t i, const Dune::FieldMatrix< K, 1, n > &subValue )
211 {
212 MakeVectorialExpression< Dune::FieldMatrix< K, 1, n >, Value > value( rangeOffset, subValue[ 0 ] );
213 functor_( offset_[ I ] + i, value );
214 }
215
216 template< class Scalar, class Vectorial >
217 void operator() ( const std::size_t i, const MakeVectorialExpression< Scalar, Vectorial > &subValue )
218 {
219 MakeVectorialExpression< Scalar, Value > value( subValue.component() + rangeOffset, subValue.scalar() );
220 functor_( offset_[ I ] + i, value );
221 }
222
223 private:
224 Functor functor_;
225 const Offset &offset_;
226 };
227
228
229
230 // TupleShapeFunctionSet::EvaluateEach
231 // -----------------------------------
232
233 template< class ... ShapeFunctionSets >
234 template< int I >
235 struct TupleShapeFunctionSet< ShapeFunctionSets ... >::EvaluateEach
236 {
237 template< class Tuple, class Point, class Functor >
238 static void apply ( const Tuple &tuple, const Offset &offset, const Point &x, Functor functor )
239 {
240 FunctorWrapper< Functor, RangeType, I > functorWrapper( functor, offset );
241 std::get< I >( tuple ).evaluateEach( x, functorWrapper );
242 }
243 };
244
245
246
247 // TupleShapeFunctionSet::JacobianEach
248 // -----------------------------------
249
250 template< class ... ShapeFunctionSets >
251 template< int I >
252 struct TupleShapeFunctionSet< ShapeFunctionSets ... >::JacobianEach
253 {
254 template< class Tuple, class Point, class Functor >
255 static void apply ( const Tuple &tuple, const Offset &offset, const Point &x, Functor functor )
256 {
257 FunctorWrapper< Functor, JacobianRangeType, I > functorWrapper( functor, offset );
258 std::get< I >( tuple ).jacobianEach( x, functorWrapper );
259 }
260 };
261
262
263
264 // TupleShapeFunctionSet::HessianEach
265 // ----------------------------------
266
267 template< class ... ShapeFunctionSets >
268 template< int I >
269 struct TupleShapeFunctionSet< ShapeFunctionSets ... >::HessianEach
270 {
271 template< class Tuple, class Point, class Functor >
272 static void apply ( const Tuple &tuple, const Offset &offset, const Point &x, Functor functor )
273 {
274 FunctorWrapper< Functor, HessianRangeType, I > functorWrapper( functor, offset );
275 std::get< I >( tuple ).hessianEach( x, functorWrapper );
276 }
277 };
278
279
280 } // namespace Fem
281
282} // namespace Dune
283
284#endif // #ifndef DUNE_FEM_SPACE_SHAPEFUNCTIONSET_TUPLE_HH
STL namespace.
Definition: bindguard.hh:11
static constexpr T max(T a)
Definition: utility.hh:77
static constexpr std::decay_t< T > sum(T a)
Definition: utility.hh:33
Definition: forloop.hh:17
convert functions space to space with new dim range
Definition: functionspace.hh:250
interface class representing a family of shape function sets
Definition: shapefunctionsets.hh:33
Definition: space/shapefunctionset/tuple.hh:26
int order() const
Definition: space/shapefunctionset/tuple.hh:106
std::tuple< ShapeFunctionSets... > shapeFunctionSetTuple_
Definition: space/shapefunctionset/tuple.hh:160
static std::tuple< decltype(makeGeometryType< I >(std::declval< GeometryType >())) ... > makeGeometryTypeTuple(GeometryType type, std::index_sequence< I ... >)
Definition: space/shapefunctionset/tuple.hh:155
TupleShapeFunctionSet(GeometryType type)
Definition: space/shapefunctionset/tuple.hh:84
const SubShapeFunctionSetType< i > & subShapeFunctionSet(std::integral_constant< std::size_t, i >={}) const
Definition: space/shapefunctionset/tuple.hh:129
FunctionSpaceType::JacobianRangeType JacobianRangeType
Definition: space/shapefunctionset/tuple.hh:78
FunctionSpaceType::RangeType RangeType
Definition: space/shapefunctionset/tuple.hh:77
TupleShapeFunctionSet()
Definition: space/shapefunctionset/tuple.hh:81
Offset offset_
Definition: space/shapefunctionset/tuple.hh:161
void evaluateEach(const Point &x, Functor functor) const
Definition: space/shapefunctionset/tuple.hh:111
FunctionSpaceType::DomainType DomainType
Definition: space/shapefunctionset/tuple.hh:76
static GeometryType makeGeometryType(GeometryType type)
Definition: space/shapefunctionset/tuple.hh:148
ToNewDimRangeFunctionSpace< typenameSubShapeFunctionSetType< 0 >::FunctionSpaceType, dimRange >::Type FunctionSpaceType
Definition: space/shapefunctionset/tuple.hh:74
TupleShapeFunctionSet(const std::tuple< ShapeFunctionSets... > &shapeFunctionSetTuple)
Definition: space/shapefunctionset/tuple.hh:99
std::size_t size() const
Definition: space/shapefunctionset/tuple.hh:108
FunctionSpaceType::HessianRangeType HessianRangeType
Definition: space/shapefunctionset/tuple.hh:79
void hessianEach(const Point &x, Functor functor) const
Definition: space/shapefunctionset/tuple.hh:123
std::tuple_element_t< i, std::tuple< ShapeFunctionSets... > > SubShapeFunctionSetType
Definition: space/shapefunctionset/tuple.hh:72
TupleShapeFunctionSet(Args &&... args)
Definition: space/shapefunctionset/tuple.hh:92
int order(std::index_sequence< I ... >) const
Definition: space/shapefunctionset/tuple.hh:136
std::size_t size(std::index_sequence< I ... >) const
Definition: space/shapefunctionset/tuple.hh:142
void jacobianEach(const Point &x, Functor functor) const
Definition: space/shapefunctionset/tuple.hh:117