SUNphi  1.0
TupleElements.hpp
Go to the documentation of this file.
1 #ifndef _TUPLEELEMENTS_HPP
2 #define _TUPLEELEMENTS_HPP
3 
4 /// \file TupleElements.hpp
5 ///
6 /// \brief Access elements of a tuple
7 
8 #include <ints/Ranges.hpp>
9 #include <metaprogramming/SFINAE.hpp>
10 #include <metaprogramming/UniversalReferences.hpp>
11 #include <tuple/TupleClass.hpp>
12 #include <tuple/TupleOrder.hpp>
13 
14 namespace SUNphi
15 {
16  /// Gets an element from the tuple.
17  ///
18  /// Directly aliasing the std library. R-value case
19  /// \return A move-reference to the I tuple element.
20  template <std::size_t I,
21  class T>
22  constexpr std::tuple_element_t<I,T>&&
23  get(T&& t)
24  {
25  return std::get<I>(forw<T>(t));
26  }
27 
28  /// Gets the element of type T from the tuple.
29  ///
30  /// Directly aliasing the std library. R-value case.
31  /// \return A move-reference to the T tuple type (if present).
32  template <class Tg,
33  class T>
34  constexpr Tg&& get(T&& t)
35  {
36  return std::get<Tg>(forw<T>(t));
37  }
38 
39  /////////////////////////////////////////////////////////////////
40 
41  /// Loop over all \c Tuple elements
42  ///
43  /// Non const access to all elements of the \c Tuple, called
44  /// recursively until I==sizeof...(Tp), incrementing the parameter
45  /// I.
46  ///
47  /// \tparam I Index of the \c Tuple element to extract
48  /// \tparam Func \c Function type
49  /// \tparam Tp... The \c Tuple parameters
50  /// \return \c void
51  template <size_t I=0,
52  typename T,
53  typename F,
54  typename=EnableIf<isTupleLike<T>>>
55  void forEach(T&& t, ///< \c Tuple to act upon
56  F&& f) ///< \c Function iterating on the \c Tuple
57  {
58  if constexpr(I<tupleSize<T>)
59  {
60  f(get<I>(forw<T>(t)));
61  forEach<I+1>(forw<T>(t),forw<F>(f));
62  }
63  }
64 
65  /////////////////////////////////////////////////////////////////////////
66 
67  /// Filter a \c Tuple on the basis of a list of index
68  ///
69  /// Return a tuple containg the elements of a tuple according to a
70  /// list of indices
71  template <typename Tp,
72  int...Ints>
73  DECLAUTO getIndexed(const IntSeq<Ints...>&,
74  Tp&& tp)
75  {
76  return
77  std::make_tuple(std::get<Ints>(forw<Tp>(tp))...);
78  }
79 
80  /// Gets the head of a \c Tuple
81  ///
82  /// Return a tuple containg the first N elements of a tuple
83  template <int N,
84  typename Tp,
85  SFINAE_ON_TEMPLATE_ARG(isTuple<Tp>)>
86  DECLAUTO getHead(Tp&& tp) ///< Tuple from which to extract
87  {
88  return
89  getIndexed(IntsUpTo<N>{},forw<Tp>(tp));
90  }
91 
92  /// Gets the tail of a \c Tuple
93  ///
94  /// Return a \c Tuple containg the last N elements of a tuple
95  template <int N,
96  typename Tp,
97  SFINAE_ON_TEMPLATE_ARG(isTuple<Tp>)>
98  DECLAUTO getTail(const Tp&& tp) ///< Tuple from which to extract
99  {
100  /// Number of elements in the tuple
101  constexpr int size=
102  tupleSize<Tp>;
103 
104  /// Beginning of returned part
105  constexpr int offset=
106  size-N;
107 
108  return
109  getIndexed(RangeSeq<offset,1,size>{},forw<Tp>(tp));
110  }
111 
112  /// Returns all elements of a \c Tuple but the N-th one
113  ///
114  /// Takes the list of component according to an index containing the
115  /// first [0,N) and (N,Sizeof...(Tuple))
116  ///
117  /// Example:
118  /// \code
119  /// Tuple<int,double,char> e;
120  /// auto GetAllBut<1>(e); // Tuple<int,char>
121  /// \endcode
122  template <int N,
123  typename Tp,
124  SFINAE_ON_TEMPLATE_ARG(isTuple<Tp>)>
125  DECLAUTO getAllButPos(Tp&& tp)
126  {
127  return getIndexed(IntSeqCat<IntsUpTo<N>,RangeSeq<N+1,1,tupleSize<Tp>>>{},forw<Tp>(tp));
128  }
129 
130  /// Returns all elements of a \c Tuple but the type T
131  ///
132  /// First search the component, then call \c GetAllBut with the
133  /// found position as a parameter
134  ///
135  /// Example:
136  /// \code
137  /// Tuple<int,double,char> e;
138  /// auto GetAllBut<double>(e); // Tuple<int,char>
139  /// \endcode
140  template <typename Tg,
141  typename Tp,
142  SFINAE_ON_TEMPLATE_ARG(isTuple<Tp>)>
143  DECLAUTO getAllButType(Tp&& tp)
144  {
145  return getAllButPos<posOfType<Tg,Tp>>(forw<Tp>(tp));
146  }
147 }
148 
149 #endif
#define SFINAE_ON_TEMPLATE_ARG(...)
Definition: SFINAE.hpp:24
constexpr Tg && get(T &&t)
#define DECLAUTO
Short name for decltype(auto)