dune-functions  2.6-dev
utility.hh
Go to the documentation of this file.
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_FUNCTIONS_COMMON_UTILITY_HH
4 #define DUNE_FUNCTIONS_COMMON_UTILITY_HH
5 
6 
7 #include <utility>
8 #include <type_traits>
9 
10 #include <dune/typetree/utility.hh>
11 
12 namespace Dune {
13 namespace Functions {
14 
15 
16 
17 template<class F, class size_type, size_type firstValue, class... Args>
18 auto forwardAsStaticInteger(std::integer_sequence<size_type, firstValue> values, const size_type& i, F&& f, Args&&... args)
19  ->decltype(f(std::integral_constant<size_type, firstValue>(), std::forward<Args>(args)...))
20 {
21  return f(std::integral_constant<size_type, firstValue>(), std::forward<Args>(args)...);
22 }
23 
24 template<class F, class size_type, size_type firstValue, size_type secondValue, size_type... otherValues, class... Args>
25 auto forwardAsStaticInteger(std::integer_sequence<size_type, firstValue, secondValue, otherValues...> values, const size_type i, F&& f, Args&&... args)
26  ->decltype(f(std::integral_constant<size_type, firstValue>(), std::forward<Args>(args)...))
27 {
28  if (i==firstValue)
29  return f(std::integral_constant<size_type, firstValue>(), std::forward<Args>(args)...);
30  return forwardAsStaticInteger(std::integer_sequence<size_type, secondValue, otherValues...>(), i, std::forward<F>(f), std::forward<Args>(args)...);
31 }
32 
33 
34 
56 template<std::size_t end, class F, class size_type, class... Args>
57 auto forwardAsStaticIndex(const size_type& i, F&& f, Args&&... args)
58  ->decltype(f(Dune::TypeTree::Indices::_0, std::forward<Args>(args)...))
59 {
60  return forwardAsStaticInteger(std::make_index_sequence<end>{}, i, std::forward<F>(f), std::forward<Args>(args)...);
61 }
62 
63 
64 
65 namespace Imp {
66 
67  template<template<class...> class T, class List>
68  struct ExpandTupleHelper
69  {};
70 
71  template<template<class...> class T, template<class...> class ListType, class... Args>
72  struct ExpandTupleHelper<T, ListType<Args...>>
73  {
74  using Type = T<Args...>;
75  };
76 
77 } // end namespace Imp
78 
90 template<template<class...> class T, class ArgTuple>
91 using ExpandTuple = typename Imp::ExpandTupleHelper<T, ArgTuple>::Type;
92 
93 
94 
95 namespace Imp {
96 
97  template<template<class...> class T, class... Tuple>
98  struct TransformTupleHelper
99  {};
100 
101  template<template<class...> class T, class... Args1>
102  struct TransformTupleHelper<T, typename std::tuple<Args1...>>
103  {
104  using Type = std::tuple<T<Args1>...>;
105  };
106 
107  template<template<class...> class T, class... Args1, class... Args2>
108  struct TransformTupleHelper<T, typename std::tuple<Args1...>, typename std::tuple<Args2...>>
109  {
110  using Type = std::tuple<T<Args1, Args2>...>;
111  };
112 
113 } // end namespace Imp
114 
127 template<template<class...> class F, class... Tuples>
128 using TransformTuple = typename Imp::TransformTupleHelper<F, Tuples...>::Type;
129 
130 
131 
132 namespace Imp {
133 
134  template<class F, class... T, std::size_t... k>
135  auto transformTupleHelper(F&& f, const std::tuple<T...>& tuple, std::index_sequence<k...>)
136  -> decltype(std::make_tuple(f(std::get<k>(tuple))...))
137  {
138  return std::make_tuple(f(std::get<k>(tuple))...);
139  }
140 
141  template<class F, class... T1, class...T2, std::size_t... k>
142  auto transformTupleHelper(F&& f, const std::tuple<T1...>& tuple1, const std::tuple<T2...>& tuple2, std::index_sequence<k...>)
143  -> decltype(std::make_tuple(f(std::get<k>(tuple1), std::get<k>(tuple2))...))
144  {
145  return std::make_tuple(f(std::get<k>(tuple1), std::get<k>(tuple2))...);
146  }
147 
148 } // end namespace Imp
149 
161 template<class F, class... T>
162 auto transformTuple(F&& f, const std::tuple<T...>& tuple)
163  -> decltype(Imp::transformTupleHelper(std::forward<F>(f), tuple, std::index_sequence_for<T...>{}))
164 {
165  return Imp::transformTupleHelper(std::forward<F>(f), tuple, std::index_sequence_for<T...>{});
166 }
167 
181 template<class F, class... T1, class... T2>
182 auto transformTuple(F&& f, const std::tuple<T1...>& tuple1, const std::tuple<T2...>& tuple2)
183  -> decltype(Imp::transformTupleHelper(std::forward<F>(f), tuple1, tuple2, std::index_sequence_for<T1...>{}))
184 {
185  return Imp::transformTupleHelper(std::forward<F>(f), tuple1, tuple2, std::index_sequence_for<T1...>{});
186 }
187 
188 
189 
190 namespace Imp {
191 
192  template<class IntegerSequence>
193  struct IntegerSequenceTupleHelper
194  {};
195 
196  template<class I, I... k>
197  struct IntegerSequenceTupleHelper<std::integer_sequence<I, k...>>
198  {
199  using Type = std::tuple<std::integral_constant<I, k>...>;
200  };
201 
202 } // end namespace Imp
203 
207 template<class IntegerSequence>
208 using IntegerSequenceTuple= typename Imp::IntegerSequenceTupleHelper<IntegerSequence>::Type;
209 
210 
211 
217 template<class... T>
218 struct LastType
219 {
220  using type = typename std::tuple_element<sizeof...(T)-1, std::tuple<T...>>::type;
221 };
222 
223 
224 
225 namespace Imp {
226 
227 template<class T, class I>
228 struct RotateHelper;
229 
230 template<class... T, std::size_t... I>
231 struct RotateHelper<std::tuple<T...>, std::index_sequence<I...> >
232 {
233  using type = typename std::tuple<typename LastType<T...>::type, typename std::tuple_element<I,std::tuple<T...>>::type...>;
234 };
235 
236 } // end namespace Imp
237 
238 
246 template<class... T>
248 {
249  using type = typename Imp::RotateHelper<std::tuple<T...>, std::make_index_sequence<sizeof...(T)-1>>::type;
250 };
251 
252 
253 
266 template<class F, class ArgTuple, class I, I... i>
267 decltype(auto) applyPartial(F&& f, ArgTuple&& args, std::integer_sequence<I, i...> indices)
268 {
269  return f(std::get<i>(args)...);
270 }
271 
272 
273 
274 } // namespace Dune::Functions
275 } // namespace Dune
276 
277 
278 #endif // DUNE_FUNCTIONS_COMMON_UTILITY_HH
auto transformTuple(F &&f, const std::tuple< T... > &tuple) -> decltype(Imp::transformTupleHelper(std::forward< F >(f), tuple, std::index_sequence_for< T... >
Transform tuple value using a functor.
Definition: utility.hh:162
auto forwardAsStaticInteger(std::integer_sequence< size_type, firstValue > values, const size_type &i, F &&f, Args &&... args) -> decltype(f(std::integral_constant< size_type, firstValue >(), std::forward< Args >(args)...))
Definition: utility.hh:18
Rotate type list by one, such that last entry is moved to first position.
Definition: utility.hh:247
Get last entry of type list.
Definition: utility.hh:218
typename Imp::TransformTupleHelper< F, Tuples... >::Type TransformTuple
Transform tuple types argument using type-functor.
Definition: utility.hh:128
typename std::tuple_element< sizeof...(T) -1, std::tuple< T... > >::type type
Definition: utility.hh:220
decltype(auto) applyPartial(F &&f, ArgTuple &&args, std::integer_sequence< I, i... > indices)
Apply function with arguments from a given tuple.
Definition: utility.hh:267
auto forwardAsStaticIndex(const size_type &i, F &&f, Args &&... args) -> decltype(f(Dune::TypeTree::Indices::_0, std::forward< Args >(args)...))
Transform dynamic index to static index_constant.
Definition: utility.hh:57
Definition: polynomial.hh:7
typename Imp::IntegerSequenceTupleHelper< IntegerSequence >::Type IntegerSequenceTuple
Transform integer_sequence<I,k...> to tuple<integral_constant<I,k>...>
Definition: utility.hh:208
typename Imp::ExpandTupleHelper< T, ArgTuple >::Type ExpandTuple
Expand tuple arguments as template arguments.
Definition: utility.hh:91
typename Imp::RotateHelper< std::tuple< T... >, std::make_index_sequence< sizeof...(T) -1 > >::type type
Definition: utility.hh:249
STL namespace.