Rheolef  7.2
an efficient C++ finite element environment
 
Loading...
Searching...
No Matches
space_constant.h
Go to the documentation of this file.
1#ifndef _RHEOLEF_SPACE_CONSTANT_H
2#define _RHEOLEF_SPACE_CONSTANT_H
23// constants
24
25#include "rheolef/undeterminated.h"
26#include "rheolef/field_expr_utilities.h"
27#include <type_traits>
28
29// ---------------------------------------------------------------------------
30// utility
31// ---------------------------------------------------------------------------
32
33namespace rheolef { namespace details {
34
35// is_equal : used by type resolution and by is_symmetric
36template <class T1, class T2> struct is_equal : std::false_type {};
37template <class T> struct is_equal<T,T> : std::true_type {};
38
39// switch for a constant, or a pointer-to-function or a class-function:
40template<class T> struct is_scalar : std::false_type {};
41template<> struct is_scalar<int> : std::true_type {};
42template<> struct is_scalar<const int> : std::true_type {};
43template<> struct is_scalar<size_t> : std::true_type {};
44template<> struct is_scalar<double> : std::true_type {};
45#ifdef _RHEOLEF_HAVE_FLOAT128
46template<> struct is_scalar<float128> : std::true_type {};
47#endif // _RHEOLEF_HAVE_FLOAT128
48
49template<class T> struct is_point : std::false_type {};
50template<class T> struct is_point<point_basic<T> > : std::true_type {};
51
52template<class T> struct is_tensor : std::false_type {};
53template<class T> struct is_tensor<tensor_basic<T> > : std::true_type {};
54
55template<class T> struct is_tensor3 : std::false_type {};
56template<class T> struct is_tensor3<tensor3_basic<T> > : std::true_type {};
57
58template<class T> struct is_tensor4 : std::false_type {};
59template<class T> struct is_tensor4<tensor4_basic<T> > : std::true_type {};
60
61} // namespace details
62// ---------------------------------------------------------------------------
63// argument promote, for template expression (binders, etc)
64// ---------------------------------------------------------------------------
65namespace details {
66template <class T1, class T2, class Sfinae = void>
68template <class T1, class T2, class Sfinae = void>
70
71#define _RHEOLEF_field_promote_argument(tensor) \
72template<class T1, class T2> \
73struct field_promote_first_argument<tensor##_basic<T1>, T2, \
74 typename std::enable_if< \
75 is_rheolef_arithmetic<T1>::value \
76 && is_rheolef_arithmetic<T2>::value \
77 >::type \
78> { \
79 using type = tensor##_basic<typename promote<T1,T2>::type>; }; \
80template <class T1, class T2> \
81struct field_promote_first_argument<T1,tensor##_basic<T2>, \
82 typename std::enable_if< \
83 is_rheolef_arithmetic<T1>::value \
84 && is_rheolef_arithmetic<T2>::value \
85 >::type \
86> { \
87 using type = typename promote<T1,T2>::type; }; \
88template <class T1, class T2> \
89struct field_promote_second_argument<tensor##_basic<T1>, T2, \
90 typename std::enable_if< \
91 is_rheolef_arithmetic<T1>::value \
92 && is_rheolef_arithmetic<T2>::value \
93 >::type \
94> { \
95 using type = typename promote<T1,T2>::type; }; \
96template <class T1, class T2> \
97struct field_promote_second_argument<T1,tensor##_basic<T2>, \
98 typename std::enable_if< \
99 is_rheolef_arithmetic<T1>::value \
100 && is_rheolef_arithmetic<T2>::value \
101 >::type \
102> { \
103 using type = tensor##_basic<typename promote<T1,T2>::type>; };
104
109#undef _RHEOLEF_field_promote_argument
110
111} // namespace details
112// -------------------------------------------------------------
113// coordinate system helper
114// -------------------------------------------------------------
115namespace space_constant {
116
117typedef size_t size_type;
118
125
126coordinate_type coordinate_system (std::string sys_coord);
129
130// -------------------------------------------------------------
131// multi-component field support
132// -------------------------------------------------------------
133typedef enum {
136 tensor = 2, // symmetric, D_ij
138 tensor3 = 4, // unsymmetric, G_ijk
139 tensor4 = 5, // symmetric, A_ijkl
140 mixed = 6,
141 last_valued = 7
143
144const std::string& valued_name (valued_type tag);
145valued_type valued_tag (const std::string& name);
146
149 size_type d,
150 coordinate_type sys_coord);
151
153 const std::string& valued,
154 size_type d,
155 coordinate_type sys_coord);
156
157// convert a type to the enum valued_tag:
158// size_t tag = valued_tag_traits<T>::value;
159template<class T> struct valued_tag_traits { static const valued_type value = scalar; };
160template<class T> struct valued_tag_traits<point_basic<T> > { static const valued_type value = vector; };
161template<class T> struct valued_tag_traits<tensor_basic<T> > { static const valued_type value = tensor; };
162template<class T> struct valued_tag_traits<tensor3_basic<T> > { static const valued_type value = tensor3; };
163template<class T> struct valued_tag_traits<tensor4_basic<T> > { static const valued_type value = tensor4; };
164template<class T> struct valued_tag_traits<undeterminated_basic<T> > { static const valued_type value = last_valued; };
165
166// convert an enum valued_tag to the type based on T:
167// typedef typename valued_type_traits<tag,T>::type valued_t;
168//
169template<int Tag, class T> struct valued_type_traits { typedef undeterminated_basic<T> type; };
170template<class T> struct valued_type_traits<scalar,T> { typedef T type; };
171template<class T> struct valued_type_traits<vector,T> { typedef point_basic<T> type; };
172template<class T> struct valued_type_traits<tensor,T> { typedef tensor_basic<T> type; };
173template<class T> struct valued_type_traits<tensor3,T> { typedef tensor3_basic<T> type; };
174template<class T> struct valued_type_traits<tensor4,T> { typedef tensor4_basic<T> type; };
175template<class T> struct valued_type_traits<last_valued,T> { typedef undeterminated_basic<T> type; };
176
177// tensorial up and down helpers (for grad(expr))
179template<class T> struct rank_down<point_basic<T> > { typedef T type; };
180template<class T> struct rank_down<tensor_basic<T> > { typedef point_basic<T> type; };
181template<class T> struct rank_down<tensor3_basic<T> > { typedef tensor_basic<T> type; };
182template<class T> struct rank_down<tensor4_basic<T> > { typedef tensor3_basic<T> type; };
183
184template<class T> struct rank_up { typedef point_basic<typename scalar_traits<T>::type> type; };
185template<class T> struct rank_up<point_basic<T> > { typedef tensor_basic<T> type; };
186template<class T> struct rank_up<tensor_basic<T> > { typedef tensor3_basic<T> type; };
187template<class T> struct rank_up<tensor3_basic<T> > { typedef tensor4_basic<T> type; };
189
190template<class T>
191T contract_product (const T& a, const T& b) { return a*b; }
192template<class T>
193T contract_product (const point_basic<T>& a, const point_basic<T>& b) { return dot(a,b); }
194template<class T>
195T contract_product (const tensor_basic<T>& a, const tensor_basic<T>& b) { return ddot(a,b); }
196
197// -------------------------------------------------------------
198// 2-tensor support
199// -------------------------------------------------------------
202 coordinate_type sys_coord,
203 size_type i,
204 size_type j);
205
207 std::string valued,
208 std::string sys_coord,
209 size_type i,
210 size_type j);
211
212std::pair<size_type,size_type>
215 coordinate_type sys_coord,
217
218std::string
221 coordinate_type sys_coord,
223
224std::pair<size_type,size_type>
226 std::string valued,
227 std::string sys_coord,
229
230std::string
232 std::string valued,
233 std::string sys_coord,
235
236// -------------------------------------------------------------
237// 4-tensor support
238// -------------------------------------------------------------
241 valued_type valued,
242 coordinate_type sys_coord,
243 size_type i,
244 size_type j,
245 size_type k,
246 size_type l);
247
250 std::string valued,
251 std::string sys_coord,
252 size_type i,
253 size_type j,
254 size_type k,
255 size_type l);
256
257std::pair<std::pair<size_type,size_type>, std::pair<size_type,size_type> >
259 valued_type valued,
260 coordinate_type sys_coord,
262
263std::string
265 valued_type valued,
266 coordinate_type sys_coord,
268
269std::pair<std::pair<size_type,size_type>, std::pair<size_type,size_type> >
271 std::string valued,
272 std::string sys_coord,
274
275std::string
277 std::string valued,
278 std::string sys_coord,
280
281// -------------------------------------------------------------
282// field*field & field/field valued_type computed at run time
283// -------------------------------------------------------------
286
287
288} // namespace space_constant
289// --------------------------------------------------------------------------
290// utility to determine whether a template arg is a function or a constant
291// --------------------------------------------------------------------------
292namespace details {
293 // build a function that returns a constant
294 template<class T1, class T2>
295 struct f_constant {
296 T2 operator() (const T1& x) const { return c; }
297 f_constant (const T2& c0) : c(c0) {}
298 const T2 c;
299 };
300 template<class F> struct is_vector_function :
301 and_type <
302 std::is_class<F>
303 ,is_point<typename F::result_type>
304 > {};
305 template<class T> struct is_vector_function<point_basic<T> (const point_basic<T>)>
306 : std::true_type {};
307
308 template<class E> class field_nonlinear_expr;
309 template<class E> struct is_expr : std::false_type {};
310 template<class E> struct is_expr<field_nonlinear_expr<E> > : std::true_type {};
311
312 template<class C>
313 struct is_constant :
314 or_type <
315 is_scalar<C>
316 ,is_point<C>
317 > {};
318
319 template<class F>
320 struct is_function :
321 and_type <
322 or_type <
323 std::is_class<F>
324 ,std::is_pointer<F>
325 ,std::is_function<F>
326 >
327 ,not_type <
328 or_type <
329 is_scalar<F>
330 ,is_point<F>
331 ,is_expr<F>
332 >
333 >
334 >
335 {};
336 template<class F>
337 struct result_type {
339 };
340 template<class T, class R>
341 struct result_type<R(const point_basic<T>&)> {
342 typedef R type;
343 };
344 template<class T, class R>
345 struct result_type<R (*)(const point_basic<T>&)> {
346 typedef R type;
347 };
348 template<class Constant>
349 struct constant_promote { typedef Constant type; };
350 template<> struct constant_promote<int> { typedef Float type; };
351 template<> struct constant_promote<size_t> { typedef Float type; };
352#ifdef _RHEOLEF_HAVE_FLOAT128
353 template<> struct constant_promote<double> { typedef Float type; };
354#endif // _RHEOLEF_HAVE_FLOAT128
355
356// constants in field expressions
357template <class Value>
359: std::disjunction<
360 is_rheolef_arithmetic<Value>
361 ,is_point<Value>
362 ,is_tensor<Value>
363 ,is_tensor3<Value>
364 ,is_tensor4<Value>
365 >
366{};
367
368}} // namespace rheolef::details
369#endif // _RHEOLEF_SPACE_CONSTITUTION_H
field::size_type size_type
Definition branch.cc:430
see the Float page for the full documentation
see the point page for the full documentation
see the tensor3 page for the full documentation
see the tensor4 page for the full documentation
see the tensor page for the full documentation
Expr1::float_type T
Definition field_expr.h:230
void check_coord_sys_and_dimension(coordinate_type i, size_type d)
coordinate_type coordinate_system(std::string sys_coord)
std::string coordinate_system_name(coordinate_type i)
valued_type multiplies_result_tag(space_constant::valued_type tag1, space_constant::valued_type tag2)
size_type tensor4_index(valued_type valued, coordinate_type sys_coord, size_type i, size_type j, size_type k, size_type l)
T contract_product(const T &a, const T &b)
std::string tensor_subscript_name(valued_type valued_tag, coordinate_type sys_coord, size_type i_comp)
size_type tensor_index(valued_type valued_tag, coordinate_type sys_coord, size_type i, size_type j)
valued_type divides_result_tag(space_constant::valued_type tag1, space_constant::valued_type tag2)
std::pair< std::pair< size_type, size_type >, std::pair< size_type, size_type > > tensor4_subscript(valued_type valued, coordinate_type sys_coord, size_type i_comp)
std::string tensor4_subscript_name(valued_type valued, coordinate_type sys_coord, size_type i_comp)
const std::string & valued_name(valued_type valued_tag)
size_type n_component(valued_type valued_tag, size_type d, coordinate_type sys_coord)
std::pair< size_type, size_type > tensor_subscript(valued_type valued_tag, coordinate_type sys_coord, size_type i_comp)
This file is part of Rheolef.
T ddot(const tensor_basic< T > &a, const tensor_basic< T > &b)
ddot(x,y): see the expression page for the full documentation
Definition tensor.cc:278
rheolef::std enable_if ::type dot const Expr1 expr1, const Expr2 expr2 dot(const Expr1 &expr1, const Expr2 &expr2)
space_constant::valued_type valued_tag() const
#define _RHEOLEF_field_promote_argument(tensor)
T2 operator()(const T1 &x) const
function_traits< F >::result_type type
undeterminated_basic< typename scalar_traits< T >::type > type
undeterminated_basic< typename scalar_traits< T >::type > type
point_basic< typename scalar_traits< T >::type > type
helper for generic field value_type: T, point_basic<T> or tensor_basic<T>