SUNphi  1.0
TupleClass.hpp
Go to the documentation of this file.
1 #ifndef _TUPLECLASS_HPP
2 #define _TUPLECLASS_HPP
3 
4 /// \file TupleClass.hpp
5 ///
6 /// \brief Define Tuple
7 
8 #include <tuple>
9 
10 #include <ints/IntSeq.hpp>
11 #include <metaprogramming/TypeTraits.hpp>
12 
13 namespace SUNphi
14 {
15  /// Define Tuple, a list of arbitrary types.
16  ///
17  /// Directly aliasing the std library.
18  template <class...Tp>
19  using Tuple=
20  std::tuple<Tp...>;
21 
22  /////////////////////////////////////////////////////////////////
23 
24  /// Check that a type is a tuple
25  ///
26  /// Generic false case
27  template <class T>
28  struct _isTuple : public FalseType
29  {
30  };
31 
32  /// Check that a type is a tuple
33  ///
34  /// Specialization for a true tuple
35  template <class...Tp>
36  struct _isTuple<Tuple<Tp...>> : public TrueType
37  {
38  };
39 
40  /// Check that a type is a tuple
41  ///
42  /// Gives visibility to the internal implementation
43  template <class T>
44  [[maybe_unused]]
45  constexpr int isTuple=
46  _isTuple<Unqualified<T>>::value;
47 
48  /// Assert if the type is not a Tuple
49 #define STATIC_ASSERT_IS_TUPLE(T)
50  static_assert(isTuple<T>,"Type is not a tuple")
51 
52  /// Constrain the class T to be a Tuple
53  template <class T>
55  {
57  };
58 
59  /////////////////////////////////////////////////////////////////
60 
61  /// Returns the type of the element I of the Tuple Tp
62  template <int I, // Order of the type in the Tuple
63  typename Tp, // Tuple type
64  typename=EnableIf<isTuple<Tp>>> // Force Tp to be a Tuple
65  using TupleElementType=
66  typename std::tuple_element<I,Tp>::type;
67 
68  /////////////////////////////////////////////////////////////////
69 
70  /// Total number of elements in a \c Tuple
71  template <typename T>
72  [[maybe_unused]]
73  constexpr int tupleSize=
74  std::tuple_size<Unqualified<T>>::value;
75 
76  /////////////////////////////////////////////////////////////////
77 
78  /// Define a Variadic type taking all types of a \c tuple as list of parameters
79  ///
80  /// Example:
81  ///
82  /// \code
83  /// template <class...Tp>
84  /// struct Test
85  /// {
86  /// int size=sizeof...(Tp);
87  /// };
88  ///
89  /// DEFINE_VARIADIC_TYPE_FROM_TUPLE(Test);
90  ///
91  /// int size=TestFromTuple<Tuple<int,char>>::size; //2
92  ///
93  /// \endcode
94 #define DEFINE_VARIADIC_TYPE_FROM_TUPLE(TYPE)
95 
96  /*! Defines a variadic type \c TYPE taking the same types of a \c Tuple */
97  /*! */
98  /*! Forward declaration of the internal implementation */
99  template <class TP,
100  class=FalseType>
101  struct _ ## TYPE ## FromTuple;
102 
103  /*! Defines a variadic type \c TYPE taking the same types of a \c Tuple */
104  /*! */
105  /*! Actual iplementation */
106  template <class...Tp>
107  struct _ ## TYPE ## FromTuple<Tuple<Tp...>>
108  {
109 
110  /*! Type which is defined out of the tuple */
111  using type=TYPE<Tp...>;
112  };
113 
114  /*! Defines a variadic type \c TYPE taking the same types of a \c Tuple */
115  /*! */
116  /*! Gives visibility to the internal implementation */
117  template <class TP,
118  class=ConstrainIsTuple<TP>>
119  using TYPE ## FromTuple=typename _ ## TYPE ## FromTuple<TP>::type
120 
121  /////////////////////////////////////////////////////////////////
122 
123  /// Counts the same types
124  ///
125  /// Single pair of types case - forbids implementation
126  template <class T1,
127  class T2,
128  class=FalseType>
129  [[ maybe_unused ]]
130  static constexpr int _nOfTypeInTuple=
131  0;
132 
133  /// Counts the same type
134  ///
135  /// Counts the occurrency of type T inside a tuple
136  template <class T,
137  class...Tp>
138  static constexpr int _nOfTypeInTuple<T,Tuple<Tp...>> =
139  hSum<isSame<T,Tp>...>;
140 
141  /// Counts the same type
142  ///
143  /// Gives external visibility to the implementation
144  template <class T,
145  class TP,
146  class=ConstrainIsTuple<TP>>
147  [[ maybe_unused ]]
148  static constexpr int nOfTypeInTuple=
149  _nOfTypeInTuple<T,TP>;
150 
151  /////////////////////////////////////////////////////////////////
152 
153  /// Count the number of different types in a \c Tuple
154  ///
155  /// Generic type - forbids instantiation
156  template <class T,
157  class=ConstrainIsTuple<T>>
158  [[ maybe_unused ]]
159  static constexpr int nDiffTypesInTuple=
160  0;
161 
162  /// Count the number of different types in a \c Tuple
163  ///
164  /// Real tuple case
165  template <class...Tp>
166  static constexpr int nDiffTypesInTuple<Tuple<Tp...>> =
167  IntSeq<(nOfTypeInTuple<Tp,Tuple<Tp...>> ==1)...>::hSum;
168 
169  /////////////////////////////////////////////////////////////////
170 
171  /// Check whether all types of a \c Tuple are different
172  template <class T,
173  class=ConstrainIsTuple<T>>
174  [[ maybe_unused ]]
175  static constexpr bool tupleTypesAreAllDifferent=
176  (nDiffTypesInTuple<T> ==tupleSize<T>);
177 
178  /// Assert if the \c Tuple contains multiple times a given type
179 #define STATIC_ASSERT_TUPLE_TYPES_ARE_ALL_DIFFERENT(T)
180  static_assert(tupleTypesAreAllDifferent<T>,"Types in the tuple are not all different")
181 
182  /// Constrain all types in the tuple to be different
183  template <class T,class=ConstrainIsTuple<T>>
185  {
187  };
188 
189  /////////////////////////////////////////////////////////////////
190 
191  /// Return true if \c Tuple Tp contains the type T
192  ///
193  /// Internal implementation
194  template <typename T, // Type to be searched
195  typename...Tp> // Tuple in which to search
196  constexpr bool _tupleHasType(T,
197  Tuple<Tp...>)
198  {
199  return (isSame<T,Tp> || ...);
200  }
201 
202  /// Return true if \c Tuple Tp contains the type T
203  template <typename T, // Type to be searched
204  typename Tp, // Tuple to search
205  typename=ConstrainIsTuple<Tp>>
206  [[ maybe_unused ]]
207  constexpr bool tupleHasType=
208  _tupleHasType(T{},Tp{});
209 
210  /// Assert if the type \c T is not in the types of tuple \c TP
211 #define STATIC_ASSERT_TUPLE_HAS_TYPE(T,
212  TP)
213  static_assert(tupleHasType<T,TP>,"Searched type not found")
214 
215  /// Constrain a type T to be contained in a \c Tuple
216  template <class T,
217  class TP,
218  class=ConstrainIsTuple<TP>>
220  {
222  };
223 
224  /// Assert if the type \c T is in the types of tuple \c TP
225 #define STATIC_ASSERT_TUPLE_HAS_NOT_TYPE(T,TP)
226  static_assert(not tupleHasType<T,TP>,"Searched type found")
227 
228  /// Constrain a type T to be not contained in a \c Tuple
229  template <class T,
230  class TP,
231  class=ConstrainIsTuple<TP>>
233  {
235  };
236 
237  /////////////////////////////////////////////////////////////////
238 
239  /// Checks that a tuple is contained into another one
240  ///
241  /// Internal implementation
242  template <typename...ToBeSearchedTypes,
243  typename...ContainingTypes>
244  constexpr bool _tupleHasTypes(Tuple<ToBeSearchedTypes...>, ///< Types to be searched
245  Tuple<ContainingTypes...>) ///< Types in which to search
246  {
247  return (tupleHasType<ToBeSearchedTypes,Tuple<ContainingTypes...>> && ...);
248  }
249 
250  /// Checks that a tuple is contained into another one
251  ///
252  /// Gives visibility to the internal implementation
253  template <typename TpToSearch,
254  typename TpContaining>
255  [[ maybe_unused ]]
256  constexpr bool tupleHasTypes=
257  _tupleHasTypes(TpToSearch{},TpContaining{});
258 }
259 
260 #endif
#define STATIC_ASSERT_TUPLE_HAS_TYPE(T,TP)
Assert if the type T is not in the types of tuple TP.
Definition: TupleClass.hpp:211
Constrain all types in the tuple to be different.
Definition: TupleClass.hpp:184
Constrain a type T to be not contained in a Tuple.
Definition: TupleClass.hpp:232
#define STATIC_ASSERT_TUPLE_TYPES_ARE_ALL_DIFFERENT(T)
Assert if the Tuple contains multiple times a given type.
Definition: TupleClass.hpp:179
#define STATIC_ASSERT_IS_TUPLE(T)
Assert if the type is not a Tuple.
Definition: TupleClass.hpp:49
Constrain the class T to be a Tuple.
Definition: TupleClass.hpp:54
constexpr int isTuple
Definition: TupleClass.hpp:45
#define STATIC_ASSERT_TUPLE_HAS_NOT_TYPE(T, TP)
Assert if the type T is in the types of tuple TP.
Definition: TupleClass.hpp:225
constexpr int tupleSize
Total number of elements in a Tuple.
Definition: TupleClass.hpp:73
Constrain a type T to be contained in a Tuple.
Definition: TupleClass.hpp:219