WPILibC++ 2023.4.3
IntegralConstant.h
Go to the documentation of this file.
1// This file is part of Eigen, a lightweight C++ template library
2// for linear algebra.
3//
4// Copyright (C) 2017 Gael Guennebaud <gael.guennebaud@inria.fr>
5//
6// This Source Code Form is subject to the terms of the Mozilla
7// Public License v. 2.0. If a copy of the MPL was not distributed
8// with this file, You can obtain one at http://mozilla.org/MPL/2.0/.
9
10
11#ifndef EIGEN_INTEGRAL_CONSTANT_H
12#define EIGEN_INTEGRAL_CONSTANT_H
13
14namespace Eigen {
15
16namespace internal {
17
18template<int N> class FixedInt;
19template<int N> class VariableAndFixedInt;
20
21/** \internal
22 * \class FixedInt
23 *
24 * This class embeds a compile-time integer \c N.
25 *
26 * It is similar to c++11 std::integral_constant<int,N> but with some additional features
27 * such as:
28 * - implicit conversion to int
29 * - arithmetic and some bitwise operators: -, +, *, /, %, &, |
30 * - c++98/14 compatibility with fix<N> and fix<N>() syntax to define integral constants.
31 *
32 * It is strongly discouraged to directly deal with this class FixedInt. Instances are expcected to
33 * be created by the user using Eigen::fix<N> or Eigen::fix<N>(). In C++98-11, the former syntax does
34 * not create a FixedInt<N> instance but rather a point to function that needs to be \em cleaned-up
35 * using the generic helper:
36 * \code
37 * internal::cleanup_index_type<T>::type
38 * internal::cleanup_index_type<T,DynamicKey>::type
39 * \endcode
40 * where T can a FixedInt<N>, a pointer to function FixedInt<N> (*)(), or numerous other integer-like representations.
41 * \c DynamicKey is either Dynamic (default) or DynamicIndex and used to identify true compile-time values.
42 *
43 * For convenience, you can extract the compile-time value \c N in a generic way using the following helper:
44 * \code
45 * internal::get_fixed_value<T,DefaultVal>::value
46 * \endcode
47 * that will give you \c N if T equals FixedInt<N> or FixedInt<N> (*)(), and \c DefaultVal if T does not embed any compile-time value (e.g., T==int).
48 *
49 * \sa fix<N>, class VariableAndFixedInt
50 */
51template<int N> class FixedInt
52{
53public:
54 static const int value = N;
55 EIGEN_CONSTEXPR operator int() const { return value; }
58 #ifndef EIGEN_INTERNAL_DEBUGGING
60 #endif
61 eigen_internal_assert(int(other)==N);
62 }
63
64 FixedInt<-N> operator-() const { return FixedInt<-N>(); }
65 template<int M>
67 template<int M>
68 FixedInt<N-M> operator-( FixedInt<M>) const { return FixedInt<N-M>(); }
69 template<int M>
71 template<int M>
72 FixedInt<N/M> operator/( FixedInt<M>) const { return FixedInt<N/M>(); }
73 template<int M>
75 template<int M>
77 template<int M>
79
80#if EIGEN_HAS_CXX14_VARIABLE_TEMPLATES
81 // Needed in C++14 to allow fix<N>():
82 FixedInt operator() () const { return *this; }
83
84 VariableAndFixedInt<N> operator() (int val) const { return VariableAndFixedInt<N>(val); }
85#else
86 FixedInt ( FixedInt<N> (*)() ) {}
87#endif
88
89#if EIGEN_HAS_CXX11
90 FixedInt(std::integral_constant<int,N>) {}
91#endif
92};
93
94/** \internal
95 * \class VariableAndFixedInt
96 *
97 * This class embeds both a compile-time integer \c N and a runtime integer.
98 * Both values are supposed to be equal unless the compile-time value \c N has a special
99 * value meaning that the runtime-value should be used. Depending on the context, this special
100 * value can be either Eigen::Dynamic (for positive quantities) or Eigen::DynamicIndex (for
101 * quantities that can be negative).
102 *
103 * It is the return-type of the function Eigen::fix<N>(int), and most of the time this is the only
104 * way it is used. It is strongly discouraged to directly deal with instances of VariableAndFixedInt.
105 * Indeed, in order to write generic code, it is the responsibility of the callee to properly convert
106 * it to either a true compile-time quantity (i.e. a FixedInt<N>), or to a runtime quantity (e.g., an Index)
107 * using the following generic helper:
108 * \code
109 * internal::cleanup_index_type<T>::type
110 * internal::cleanup_index_type<T,DynamicKey>::type
111 * \endcode
112 * where T can be a template instantiation of VariableAndFixedInt or numerous other integer-like representations.
113 * \c DynamicKey is either Dynamic (default) or DynamicIndex and used to identify true compile-time values.
114 *
115 * For convenience, you can also extract the compile-time value \c N using the following helper:
116 * \code
117 * internal::get_fixed_value<T,DefaultVal>::value
118 * \endcode
119 * that will give you \c N if T equals VariableAndFixedInt<N>, and \c DefaultVal if T does not embed any compile-time value (e.g., T==int).
120 *
121 * \sa fix<N>(int), class FixedInt
122 */
123template<int N> class VariableAndFixedInt
124{
125public:
126 static const int value = N;
127 operator int() const { return m_value; }
128 VariableAndFixedInt(int val) { m_value = val; }
129protected:
131};
132
133template<typename T, int Default=Dynamic> struct get_fixed_value {
134 static const int value = Default;
135};
136
137template<int N,int Default> struct get_fixed_value<FixedInt<N>,Default> {
138 static const int value = N;
139};
140
141#if !EIGEN_HAS_CXX14
142template<int N,int Default> struct get_fixed_value<FixedInt<N> (*)(),Default> {
143 static const int value = N;
144};
145#endif
146
147template<int N,int Default> struct get_fixed_value<VariableAndFixedInt<N>,Default> {
148 static const int value = N ;
149};
150
151template<typename T, int N, int Default>
153 static const int value = N;
154};
155
156template<typename T> EIGEN_DEVICE_FUNC Index get_runtime_value(const T &x) { return x; }
157#if !EIGEN_HAS_CXX14
158template<int N> EIGEN_DEVICE_FUNC Index get_runtime_value(FixedInt<N> (*)()) { return N; }
159#endif
160
161// Cleanup integer/FixedInt/VariableAndFixedInt/etc types:
162
163// By default, no cleanup:
164template<typename T, int DynamicKey=Dynamic, typename EnableIf=void> struct cleanup_index_type { typedef T type; };
165
166// Convert any integral type (e.g., short, int, unsigned int, etc.) to Eigen::Index
167template<typename T, int DynamicKey> struct cleanup_index_type<T,DynamicKey,typename internal::enable_if<internal::is_integral<T>::value>::type> { typedef Index type; };
168
169#if !EIGEN_HAS_CXX14
170// In c++98/c++11, fix<N> is a pointer to function that we better cleanup to a true FixedInt<N>:
171template<int N, int DynamicKey> struct cleanup_index_type<FixedInt<N> (*)(), DynamicKey> { typedef FixedInt<N> type; };
172#endif
173
174// If VariableAndFixedInt does not match DynamicKey, then we turn it to a pure compile-time value:
175template<int N, int DynamicKey> struct cleanup_index_type<VariableAndFixedInt<N>, DynamicKey> { typedef FixedInt<N> type; };
176// If VariableAndFixedInt matches DynamicKey, then we turn it to a pure runtime-value (aka Index):
177template<int DynamicKey> struct cleanup_index_type<VariableAndFixedInt<DynamicKey>, DynamicKey> { typedef Index type; };
178
179#if EIGEN_HAS_CXX11
180template<int N, int DynamicKey> struct cleanup_index_type<std::integral_constant<int,N>, DynamicKey> { typedef FixedInt<N> type; };
181#endif
182
183} // end namespace internal
184
185#ifndef EIGEN_PARSED_BY_DOXYGEN
186
187#if EIGEN_HAS_CXX14_VARIABLE_TEMPLATES
188template<int N>
189static const internal::FixedInt<N> fix{};
190#else
191template<int N>
193
194// The generic typename T is mandatory. Otherwise, a code like fix<N> could refer to either the function above or this next overload.
195// This way a code like fix<N> can only refer to the previous function.
196template<int N,typename T>
197inline internal::VariableAndFixedInt<N> fix(T val) { return internal::VariableAndFixedInt<N>(internal::convert_index<int>(val)); }
198#endif
199
200#else // EIGEN_PARSED_BY_DOXYGEN
201
202/** \var fix<N>()
203 * \ingroup Core_Module
204 *
205 * This \em identifier permits to construct an object embedding a compile-time integer \c N.
206 *
207 * \tparam N the compile-time integer value
208 *
209 * It is typically used in conjunction with the Eigen::seq and Eigen::seqN functions to pass compile-time values to them:
210 * \code
211 * seqN(10,fix<4>,fix<-3>) // <=> [10 7 4 1]
212 * \endcode
213 *
214 * See also the function fix(int) to pass both a compile-time and runtime value.
215 *
216 * In c++14, it is implemented as:
217 * \code
218 * template<int N> static const internal::FixedInt<N> fix{};
219 * \endcode
220 * where internal::FixedInt<N> is an internal template class similar to
221 * <a href="http://en.cppreference.com/w/cpp/types/integral_constant">\c std::integral_constant </a><tt> <int,N> </tt>
222 * Here, \c fix<N> is thus an object of type \c internal::FixedInt<N>.
223 *
224 * In c++98/11, it is implemented as a function:
225 * \code
226 * template<int N> inline internal::FixedInt<N> fix();
227 * \endcode
228 * Here internal::FixedInt<N> is thus a pointer to function.
229 *
230 * If for some reason you want a true object in c++98 then you can write: \code fix<N>() \endcode which is also valid in c++14.
231 *
232 * \sa fix<N>(int), seq, seqN
233 */
234template<int N>
235static const auto fix();
236
237/** \fn fix<N>(int)
238 * \ingroup Core_Module
239 *
240 * This function returns an object embedding both a compile-time integer \c N, and a fallback runtime value \a val.
241 *
242 * \tparam N the compile-time integer value
243 * \param val the fallback runtime integer value
244 *
245 * This function is a more general version of the \ref fix identifier/function that can be used in template code
246 * where the compile-time value could turn out to actually mean "undefined at compile-time". For positive integers
247 * such as a size or a dimension, this case is identified by Eigen::Dynamic, whereas runtime signed integers
248 * (e.g., an increment/stride) are identified as Eigen::DynamicIndex. In such a case, the runtime value \a val
249 * will be used as a fallback.
250 *
251 * A typical use case would be:
252 * \code
253 * template<typename Derived> void foo(const MatrixBase<Derived> &mat) {
254 * const int N = Derived::RowsAtCompileTime==Dynamic ? Dynamic : Derived::RowsAtCompileTime/2;
255 * const int n = mat.rows()/2;
256 * ... mat( seqN(0,fix<N>(n) ) ...;
257 * }
258 * \endcode
259 * In this example, the function Eigen::seqN knows that the second argument is expected to be a size.
260 * If the passed compile-time value N equals Eigen::Dynamic, then the proxy object returned by fix will be dissmissed, and converted to an Eigen::Index of value \c n.
261 * Otherwise, the runtime-value \c n will be dissmissed, and the returned ArithmeticSequence will be of the exact same type as <tt> seqN(0,fix<N>) </tt>.
262 *
263 * \sa fix, seqN, class ArithmeticSequence
264 */
265template<int N>
266static const auto fix(int val);
267
268#endif // EIGEN_PARSED_BY_DOXYGEN
269
270} // end namespace Eigen
271
272#endif // EIGEN_INTEGRAL_CONSTANT_H
internal::enable_if< internal::valid_indexed_view_overload< RowIndices, ColIndices >::value &&internal::traits< typenameEIGEN_INDEXED_VIEW_METHOD_TYPE< RowIndices, ColIndices >::type >::ReturnAsIndexedView, typenameEIGEN_INDEXED_VIEW_METHOD_TYPE< RowIndices, ColIndices >::type >::type operator()(const RowIndices &rowIndices, const ColIndices &colIndices) EIGEN_INDEXED_VIEW_METHOD_CONST
Definition: IndexedViewMethods.h:73
#define eigen_internal_assert(x)
Definition: Macros.h:1053
#define EIGEN_CONSTEXPR
Definition: Macros.h:797
#define EIGEN_UNUSED_VARIABLE(var)
Definition: Macros.h:1086
#define EIGEN_DEVICE_FUNC
Definition: Macros.h:986
Definition: IntegralConstant.h:52
FixedInt< N|M > operator|(FixedInt< M >) const
Definition: IntegralConstant.h:76
FixedInt<-N > operator-() const
Definition: IntegralConstant.h:64
FixedInt< N/M > operator/(FixedInt< M >) const
Definition: IntegralConstant.h:72
static const int value
Definition: IntegralConstant.h:54
FixedInt(FixedInt< N >(*)())
Definition: IntegralConstant.h:86
FixedInt(VariableAndFixedInt< N > other)
Definition: IntegralConstant.h:57
FixedInt()
Definition: IntegralConstant.h:56
FixedInt< N+M > operator+(FixedInt< M >) const
Definition: IntegralConstant.h:66
FixedInt< N%M > operator%(FixedInt< M >) const
Definition: IntegralConstant.h:74
FixedInt< N &M > operator&(FixedInt< M >) const
Definition: IntegralConstant.h:78
FixedInt< N *M > operator*(FixedInt< M >) const
Definition: IntegralConstant.h:70
FixedInt< N-M > operator-(FixedInt< M >) const
Definition: IntegralConstant.h:68
Definition: IntegralConstant.h:124
int m_value
Definition: IntegralConstant.h:130
VariableAndFixedInt(int val)
Definition: IntegralConstant.h:128
Definition: XprHelper.h:130
Definition: core.h:1240
type
Definition: core.h:575
EIGEN_DEVICE_FUNC Index get_runtime_value(const T &x)
Definition: IntegralConstant.h:156
Namespace containing all symbols from the Eigen library.
Definition: MatrixExponential.h:16
EIGEN_DEFAULT_DENSE_INDEX_TYPE Index
The Index type as used for the API.
Definition: Meta.h:74
@ Default
Definition: Constants.h:362
internal::FixedInt< N > fix()
Definition: IntegralConstant.h:192
Definition: Eigen_Colamd.h:50
Definition: StdDeque.h:50
FixedInt< N > type
Definition: IntegralConstant.h:171
Definition: IntegralConstant.h:164
T type
Definition: IntegralConstant.h:164
Definition: Meta.h:273
Definition: IntegralConstant.h:133