/src/eigen/Eigen/src/Core/DenseCoeffsBase.h
Line | Count | Source (jump to first uncovered line) |
1 | | // This file is part of Eigen, a lightweight C++ template library |
2 | | // for linear algebra. |
3 | | // |
4 | | // Copyright (C) 2006-2010 Benoit Jacob <jacob.benoit.1@gmail.com> |
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 | | #ifndef EIGEN_DENSECOEFFSBASE_H |
11 | | #define EIGEN_DENSECOEFFSBASE_H |
12 | | |
13 | | // IWYU pragma: private |
14 | | #include "./InternalHeaderCheck.h" |
15 | | |
16 | | namespace Eigen { |
17 | | |
18 | | namespace internal { |
19 | | template <typename T> |
20 | | struct add_const_on_value_type_if_arithmetic { |
21 | | typedef std::conditional_t<is_arithmetic<T>::value, T, add_const_on_value_type_t<T>> type; |
22 | | }; |
23 | | } // namespace internal |
24 | | |
25 | | /** \brief Base class providing read-only coefficient access to matrices and arrays. |
26 | | * \ingroup Core_Module |
27 | | * \tparam Derived Type of the derived class |
28 | | * |
29 | | * \note #ReadOnlyAccessors Constant indicating read-only access |
30 | | * |
31 | | * This class defines the \c operator() \c const function and friends, which can be used to read specific |
32 | | * entries of a matrix or array. |
33 | | * |
34 | | * \sa DenseCoeffsBase<Derived, WriteAccessors>, DenseCoeffsBase<Derived, DirectAccessors>, |
35 | | * \ref TopicClassHierarchy |
36 | | */ |
37 | | template <typename Derived> |
38 | | class DenseCoeffsBase<Derived, ReadOnlyAccessors> : public EigenBase<Derived> { |
39 | | public: |
40 | | typedef typename internal::traits<Derived>::StorageKind StorageKind; |
41 | | typedef typename internal::traits<Derived>::Scalar Scalar; |
42 | | typedef typename internal::packet_traits<Scalar>::type PacketScalar; |
43 | | |
44 | | // Explanation for this CoeffReturnType typedef. |
45 | | // - This is the return type of the coeff() method. |
46 | | // - The LvalueBit means exactly that we can offer a coeffRef() method, which means exactly that we can get references |
47 | | // to coeffs, which means exactly that we can have coeff() return a const reference (as opposed to returning a value). |
48 | | // - The is_arithmetic check is required since "const int", "const double", etc. will cause warnings on some systems |
49 | | // while the declaration of "const T", where T is a non arithmetic type does not. Always returning "const Scalar&" is |
50 | | // not possible, since the underlying expressions might not offer a valid address the reference could be referring to. |
51 | | typedef std::conditional_t<bool(internal::traits<Derived>::Flags& LvalueBit), const Scalar&, |
52 | | std::conditional_t<internal::is_arithmetic<Scalar>::value, Scalar, const Scalar>> |
53 | | CoeffReturnType; |
54 | | |
55 | | typedef typename internal::add_const_on_value_type_if_arithmetic<typename internal::packet_traits<Scalar>::type>::type |
56 | | PacketReturnType; |
57 | | |
58 | | typedef EigenBase<Derived> Base; |
59 | | using Base::cols; |
60 | | using Base::derived; |
61 | | using Base::rows; |
62 | | using Base::size; |
63 | | |
64 | | EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE Index rowIndexByOuterInner(Index outer, Index inner) const { |
65 | | return int(Derived::RowsAtCompileTime) == 1 ? 0 |
66 | | : int(Derived::ColsAtCompileTime) == 1 ? inner |
67 | | : int(Derived::Flags) & RowMajorBit ? outer |
68 | | : inner; |
69 | | } |
70 | | |
71 | | EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE Index colIndexByOuterInner(Index outer, Index inner) const { |
72 | | return int(Derived::ColsAtCompileTime) == 1 ? 0 |
73 | | : int(Derived::RowsAtCompileTime) == 1 ? inner |
74 | | : int(Derived::Flags) & RowMajorBit ? inner |
75 | | : outer; |
76 | | } |
77 | | |
78 | | /** Short version: don't use this function, use |
79 | | * \link operator()(Index,Index) const \endlink instead. |
80 | | * |
81 | | * Long version: this function is similar to |
82 | | * \link operator()(Index,Index) const \endlink, but without the assertion. |
83 | | * Use this for limiting the performance cost of debugging code when doing |
84 | | * repeated coefficient access. Only use this when it is guaranteed that the |
85 | | * parameters \a row and \a col are in range. |
86 | | * |
87 | | * If EIGEN_INTERNAL_DEBUGGING is defined, an assertion will be made, making this |
88 | | * function equivalent to \link operator()(Index,Index) const \endlink. |
89 | | * |
90 | | * \sa operator()(Index,Index) const, coeffRef(Index,Index), coeff(Index) const |
91 | | */ |
92 | | EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE CoeffReturnType coeff(Index row, Index col) const { |
93 | | eigen_internal_assert(row >= 0 && row < rows() && col >= 0 && col < cols()); |
94 | | return internal::evaluator<Derived>(derived()).coeff(row, col); |
95 | | } |
96 | | |
97 | | EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE CoeffReturnType coeffByOuterInner(Index outer, Index inner) const { |
98 | | return coeff(rowIndexByOuterInner(outer, inner), colIndexByOuterInner(outer, inner)); |
99 | | } |
100 | | |
101 | | /** \returns the coefficient at given the given row and column. |
102 | | * |
103 | | * \sa operator()(Index,Index), operator[](Index) |
104 | | */ |
105 | | EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE CoeffReturnType operator()(Index row, Index col) const { |
106 | | eigen_assert(row >= 0 && row < rows() && col >= 0 && col < cols()); |
107 | | return coeff(row, col); |
108 | | } |
109 | | |
110 | | /** Short version: don't use this function, use |
111 | | * \link operator[](Index) const \endlink instead. |
112 | | * |
113 | | * Long version: this function is similar to |
114 | | * \link operator[](Index) const \endlink, but without the assertion. |
115 | | * Use this for limiting the performance cost of debugging code when doing |
116 | | * repeated coefficient access. Only use this when it is guaranteed that the |
117 | | * parameter \a index is in range. |
118 | | * |
119 | | * If EIGEN_INTERNAL_DEBUGGING is defined, an assertion will be made, making this |
120 | | * function equivalent to \link operator[](Index) const \endlink. |
121 | | * |
122 | | * \sa operator[](Index) const, coeffRef(Index), coeff(Index,Index) const |
123 | | */ |
124 | | |
125 | | EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE CoeffReturnType coeff(Index index) const { |
126 | | EIGEN_STATIC_ASSERT(internal::evaluator<Derived>::Flags & LinearAccessBit, |
127 | | THIS_COEFFICIENT_ACCESSOR_TAKING_ONE_ACCESS_IS_ONLY_FOR_EXPRESSIONS_ALLOWING_LINEAR_ACCESS) |
128 | | eigen_internal_assert(index >= 0 && index < size()); |
129 | | return internal::evaluator<Derived>(derived()).coeff(index); |
130 | | } |
131 | | |
132 | | /** \returns the coefficient at given index. |
133 | | * |
134 | | * This method is allowed only for vector expressions, and for matrix expressions having the LinearAccessBit. |
135 | | * |
136 | | * \sa operator[](Index), operator()(Index,Index) const, x() const, y() const, |
137 | | * z() const, w() const |
138 | | */ |
139 | | |
140 | | EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE CoeffReturnType operator[](Index index) const { |
141 | | EIGEN_STATIC_ASSERT(Derived::IsVectorAtCompileTime, |
142 | | THE_BRACKET_OPERATOR_IS_ONLY_FOR_VECTORS__USE_THE_PARENTHESIS_OPERATOR_INSTEAD) |
143 | | eigen_assert(index >= 0 && index < size()); |
144 | | return coeff(index); |
145 | | } |
146 | | |
147 | | /** \returns the coefficient at given index. |
148 | | * |
149 | | * This is synonymous to operator[](Index) const. |
150 | | * |
151 | | * This method is allowed only for vector expressions, and for matrix expressions having the LinearAccessBit. |
152 | | * |
153 | | * \sa operator[](Index), operator()(Index,Index) const, x() const, y() const, |
154 | | * z() const, w() const |
155 | | */ |
156 | | |
157 | | EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE CoeffReturnType operator()(Index index) const { |
158 | | eigen_assert(index >= 0 && index < size()); |
159 | | return coeff(index); |
160 | | } |
161 | | |
162 | | /** equivalent to operator[](0). */ |
163 | | |
164 | | EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE CoeffReturnType x() const { return (*this)[0]; } |
165 | | |
166 | | /** equivalent to operator[](1). */ |
167 | | |
168 | | EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE CoeffReturnType y() const { |
169 | | EIGEN_STATIC_ASSERT(Derived::SizeAtCompileTime == -1 || Derived::SizeAtCompileTime >= 2, OUT_OF_RANGE_ACCESS); |
170 | | return (*this)[1]; |
171 | | } |
172 | | |
173 | | /** equivalent to operator[](2). */ |
174 | | |
175 | | EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE CoeffReturnType z() const { |
176 | | EIGEN_STATIC_ASSERT(Derived::SizeAtCompileTime == -1 || Derived::SizeAtCompileTime >= 3, OUT_OF_RANGE_ACCESS); |
177 | | return (*this)[2]; |
178 | | } |
179 | | |
180 | | /** equivalent to operator[](3). */ |
181 | | |
182 | | EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE CoeffReturnType w() const { |
183 | | EIGEN_STATIC_ASSERT(Derived::SizeAtCompileTime == -1 || Derived::SizeAtCompileTime >= 4, OUT_OF_RANGE_ACCESS); |
184 | | return (*this)[3]; |
185 | | } |
186 | | |
187 | | /** \internal |
188 | | * \returns the packet of coefficients starting at the given row and column. It is your responsibility |
189 | | * to ensure that a packet really starts there. This method is only available on expressions having the |
190 | | * PacketAccessBit. |
191 | | * |
192 | | * The \a LoadMode parameter may have the value \a #Aligned or \a #Unaligned. Its effect is to select |
193 | | * the appropriate vectorization instruction. Aligned access is faster, but is only possible for packets |
194 | | * starting at an address which is a multiple of the packet size. |
195 | | */ |
196 | | |
197 | | template <int LoadMode> |
198 | | EIGEN_STRONG_INLINE PacketReturnType packet(Index row, Index col) const { |
199 | | typedef typename internal::packet_traits<Scalar>::type DefaultPacketType; |
200 | | eigen_internal_assert(row >= 0 && row < rows() && col >= 0 && col < cols()); |
201 | | return internal::evaluator<Derived>(derived()).template packet<LoadMode, DefaultPacketType>(row, col); |
202 | | } |
203 | | |
204 | | /** \internal */ |
205 | | template <int LoadMode> |
206 | | EIGEN_STRONG_INLINE PacketReturnType packetByOuterInner(Index outer, Index inner) const { |
207 | | return packet<LoadMode>(rowIndexByOuterInner(outer, inner), colIndexByOuterInner(outer, inner)); |
208 | | } |
209 | | |
210 | | /** \internal |
211 | | * \returns the packet of coefficients starting at the given index. It is your responsibility |
212 | | * to ensure that a packet really starts there. This method is only available on expressions having the |
213 | | * PacketAccessBit and the LinearAccessBit. |
214 | | * |
215 | | * The \a LoadMode parameter may have the value \a #Aligned or \a #Unaligned. Its effect is to select |
216 | | * the appropriate vectorization instruction. Aligned access is faster, but is only possible for packets |
217 | | * starting at an address which is a multiple of the packet size. |
218 | | */ |
219 | | |
220 | | template <int LoadMode> |
221 | | EIGEN_STRONG_INLINE PacketReturnType packet(Index index) const { |
222 | | EIGEN_STATIC_ASSERT(internal::evaluator<Derived>::Flags & LinearAccessBit, |
223 | | THIS_COEFFICIENT_ACCESSOR_TAKING_ONE_ACCESS_IS_ONLY_FOR_EXPRESSIONS_ALLOWING_LINEAR_ACCESS) |
224 | | typedef typename internal::packet_traits<Scalar>::type DefaultPacketType; |
225 | | eigen_internal_assert(index >= 0 && index < size()); |
226 | | return internal::evaluator<Derived>(derived()).template packet<LoadMode, DefaultPacketType>(index); |
227 | | } |
228 | | |
229 | | protected: |
230 | | // explanation: DenseBase is doing "using ..." on the methods from DenseCoeffsBase. |
231 | | // But some methods are only available in the DirectAccess case. |
232 | | // So we add dummy methods here with these names, so that "using... " doesn't fail. |
233 | | // It's not private so that the child class DenseBase can access them, and it's not public |
234 | | // either since it's an implementation detail, so has to be protected. |
235 | | void coeffRef(); |
236 | | void coeffRefByOuterInner(); |
237 | | void writePacket(); |
238 | | void writePacketByOuterInner(); |
239 | | void copyCoeff(); |
240 | | void copyCoeffByOuterInner(); |
241 | | void copyPacket(); |
242 | | void copyPacketByOuterInner(); |
243 | | void stride(); |
244 | | void innerStride(); |
245 | | void outerStride(); |
246 | | void rowStride(); |
247 | | void colStride(); |
248 | | }; |
249 | | |
250 | | /** \brief Base class providing read/write coefficient access to matrices and arrays. |
251 | | * \ingroup Core_Module |
252 | | * \tparam Derived Type of the derived class |
253 | | * |
254 | | * \note #WriteAccessors Constant indicating read/write access |
255 | | * |
256 | | * This class defines the non-const \c operator() function and friends, which can be used to write specific |
257 | | * entries of a matrix or array. This class inherits DenseCoeffsBase<Derived, ReadOnlyAccessors> which |
258 | | * defines the const variant for reading specific entries. |
259 | | * |
260 | | * \sa DenseCoeffsBase<Derived, DirectAccessors>, \ref TopicClassHierarchy |
261 | | */ |
262 | | template <typename Derived> |
263 | | class DenseCoeffsBase<Derived, WriteAccessors> : public DenseCoeffsBase<Derived, ReadOnlyAccessors> { |
264 | | public: |
265 | | typedef DenseCoeffsBase<Derived, ReadOnlyAccessors> Base; |
266 | | |
267 | | typedef typename internal::traits<Derived>::StorageKind StorageKind; |
268 | | typedef typename internal::traits<Derived>::Scalar Scalar; |
269 | | typedef typename internal::packet_traits<Scalar>::type PacketScalar; |
270 | | typedef typename NumTraits<Scalar>::Real RealScalar; |
271 | | |
272 | | using Base::coeff; |
273 | | using Base::colIndexByOuterInner; |
274 | | using Base::cols; |
275 | | using Base::derived; |
276 | | using Base::rowIndexByOuterInner; |
277 | | using Base::rows; |
278 | | using Base::size; |
279 | | using Base::operator[]; |
280 | | using Base::operator(); |
281 | | using Base::w; |
282 | | using Base::x; |
283 | | using Base::y; |
284 | | using Base::z; |
285 | | |
286 | | /** Short version: don't use this function, use |
287 | | * \link operator()(Index,Index) \endlink instead. |
288 | | * |
289 | | * Long version: this function is similar to |
290 | | * \link operator()(Index,Index) \endlink, but without the assertion. |
291 | | * Use this for limiting the performance cost of debugging code when doing |
292 | | * repeated coefficient access. Only use this when it is guaranteed that the |
293 | | * parameters \a row and \a col are in range. |
294 | | * |
295 | | * If EIGEN_INTERNAL_DEBUGGING is defined, an assertion will be made, making this |
296 | | * function equivalent to \link operator()(Index,Index) \endlink. |
297 | | * |
298 | | * \sa operator()(Index,Index), coeff(Index, Index) const, coeffRef(Index) |
299 | | */ |
300 | 18.6M | EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE Scalar& coeffRef(Index row, Index col) { |
301 | 18.6M | eigen_internal_assert(row >= 0 && row < rows() && col >= 0 && col < cols()); |
302 | 18.6M | return internal::evaluator<Derived>(derived()).coeffRef(row, col); |
303 | 18.6M | } |
304 | | |
305 | | EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE Scalar& coeffRefByOuterInner(Index outer, Index inner) { |
306 | | return coeffRef(rowIndexByOuterInner(outer, inner), colIndexByOuterInner(outer, inner)); |
307 | | } |
308 | | |
309 | | /** \returns a reference to the coefficient at given the given row and column. |
310 | | * |
311 | | * \sa operator[](Index) |
312 | | */ |
313 | | |
314 | 18.6M | EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE Scalar& operator()(Index row, Index col) { |
315 | 18.6M | eigen_assert(row >= 0 && row < rows() && col >= 0 && col < cols()); |
316 | 0 | return coeffRef(row, col); |
317 | 18.6M | } |
318 | | |
319 | | /** Short version: don't use this function, use |
320 | | * \link operator[](Index) \endlink instead. |
321 | | * |
322 | | * Long version: this function is similar to |
323 | | * \link operator[](Index) \endlink, but without the assertion. |
324 | | * Use this for limiting the performance cost of debugging code when doing |
325 | | * repeated coefficient access. Only use this when it is guaranteed that the |
326 | | * parameters \a row and \a col are in range. |
327 | | * |
328 | | * If EIGEN_INTERNAL_DEBUGGING is defined, an assertion will be made, making this |
329 | | * function equivalent to \link operator[](Index) \endlink. |
330 | | * |
331 | | * \sa operator[](Index), coeff(Index) const, coeffRef(Index,Index) |
332 | | */ |
333 | | |
334 | 41.0k | EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE Scalar& coeffRef(Index index) { |
335 | 41.0k | EIGEN_STATIC_ASSERT(internal::evaluator<Derived>::Flags & LinearAccessBit, |
336 | 41.0k | THIS_COEFFICIENT_ACCESSOR_TAKING_ONE_ACCESS_IS_ONLY_FOR_EXPRESSIONS_ALLOWING_LINEAR_ACCESS) |
337 | 41.0k | eigen_internal_assert(index >= 0 && index < size()); |
338 | 41.0k | return internal::evaluator<Derived>(derived()).coeffRef(index); |
339 | 41.0k | } |
340 | | |
341 | | /** \returns a reference to the coefficient at given index. |
342 | | * |
343 | | * This method is allowed only for vector expressions, and for matrix expressions having the LinearAccessBit. |
344 | | * |
345 | | * \sa operator[](Index) const, operator()(Index,Index), x(), y(), z(), w() |
346 | | */ |
347 | | |
348 | | EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE Scalar& operator[](Index index) { |
349 | | EIGEN_STATIC_ASSERT(Derived::IsVectorAtCompileTime, |
350 | | THE_BRACKET_OPERATOR_IS_ONLY_FOR_VECTORS__USE_THE_PARENTHESIS_OPERATOR_INSTEAD) |
351 | | eigen_assert(index >= 0 && index < size()); |
352 | | return coeffRef(index); |
353 | | } |
354 | | |
355 | | /** \returns a reference to the coefficient at given index. |
356 | | * |
357 | | * This is synonymous to operator[](Index). |
358 | | * |
359 | | * This method is allowed only for vector expressions, and for matrix expressions having the LinearAccessBit. |
360 | | * |
361 | | * \sa operator[](Index) const, operator()(Index,Index), x(), y(), z(), w() |
362 | | */ |
363 | | |
364 | 41.0k | EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE Scalar& operator()(Index index) { |
365 | 41.0k | eigen_assert(index >= 0 && index < size()); |
366 | 0 | return coeffRef(index); |
367 | 41.0k | } |
368 | | |
369 | | /** equivalent to operator[](0). */ |
370 | | |
371 | | EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE Scalar& x() { return (*this)[0]; } |
372 | | |
373 | | /** equivalent to operator[](1). */ |
374 | | |
375 | | EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE Scalar& y() { |
376 | | EIGEN_STATIC_ASSERT(Derived::SizeAtCompileTime == -1 || Derived::SizeAtCompileTime >= 2, OUT_OF_RANGE_ACCESS); |
377 | | return (*this)[1]; |
378 | | } |
379 | | |
380 | | /** equivalent to operator[](2). */ |
381 | | |
382 | | EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE Scalar& z() { |
383 | | EIGEN_STATIC_ASSERT(Derived::SizeAtCompileTime == -1 || Derived::SizeAtCompileTime >= 3, OUT_OF_RANGE_ACCESS); |
384 | | return (*this)[2]; |
385 | | } |
386 | | |
387 | | /** equivalent to operator[](3). */ |
388 | | |
389 | | EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE Scalar& w() { |
390 | | EIGEN_STATIC_ASSERT(Derived::SizeAtCompileTime == -1 || Derived::SizeAtCompileTime >= 4, OUT_OF_RANGE_ACCESS); |
391 | | return (*this)[3]; |
392 | | } |
393 | | }; |
394 | | |
395 | | /** \brief Base class providing direct read-only coefficient access to matrices and arrays. |
396 | | * \ingroup Core_Module |
397 | | * \tparam Derived Type of the derived class |
398 | | * |
399 | | * \note #DirectAccessors Constant indicating direct access |
400 | | * |
401 | | * This class defines functions to work with strides which can be used to access entries directly. This class |
402 | | * inherits DenseCoeffsBase<Derived, ReadOnlyAccessors> which defines functions to access entries read-only using |
403 | | * \c operator() . |
404 | | * |
405 | | * \sa \blank \ref TopicClassHierarchy |
406 | | */ |
407 | | template <typename Derived> |
408 | | class DenseCoeffsBase<Derived, DirectAccessors> : public DenseCoeffsBase<Derived, ReadOnlyAccessors> { |
409 | | public: |
410 | | typedef DenseCoeffsBase<Derived, ReadOnlyAccessors> Base; |
411 | | typedef typename internal::traits<Derived>::Scalar Scalar; |
412 | | typedef typename NumTraits<Scalar>::Real RealScalar; |
413 | | |
414 | | using Base::cols; |
415 | | using Base::derived; |
416 | | using Base::rows; |
417 | | using Base::size; |
418 | | |
419 | | /** \returns the pointer increment between two consecutive elements within a slice in the inner direction. |
420 | | * |
421 | | * \sa outerStride(), rowStride(), colStride() |
422 | | */ |
423 | | EIGEN_DEVICE_FUNC EIGEN_CONSTEXPR inline Index innerStride() const { return derived().innerStride(); } |
424 | | |
425 | | /** \returns the pointer increment between two consecutive inner slices (for example, between two consecutive columns |
426 | | * in a column-major matrix). |
427 | | * |
428 | | * \sa innerStride(), rowStride(), colStride() |
429 | | */ |
430 | | EIGEN_DEVICE_FUNC EIGEN_CONSTEXPR inline Index outerStride() const { return derived().outerStride(); } |
431 | | |
432 | | // FIXME shall we remove it ? |
433 | | EIGEN_CONSTEXPR inline Index stride() const { return Derived::IsVectorAtCompileTime ? innerStride() : outerStride(); } |
434 | | |
435 | | /** \returns the pointer increment between two consecutive rows. |
436 | | * |
437 | | * \sa innerStride(), outerStride(), colStride() |
438 | | */ |
439 | | EIGEN_DEVICE_FUNC EIGEN_CONSTEXPR inline Index rowStride() const { |
440 | | return Derived::IsRowMajor ? outerStride() : innerStride(); |
441 | | } |
442 | | |
443 | | /** \returns the pointer increment between two consecutive columns. |
444 | | * |
445 | | * \sa innerStride(), outerStride(), rowStride() |
446 | | */ |
447 | | EIGEN_DEVICE_FUNC EIGEN_CONSTEXPR inline Index colStride() const { |
448 | | return Derived::IsRowMajor ? innerStride() : outerStride(); |
449 | | } |
450 | | }; |
451 | | |
452 | | /** \brief Base class providing direct read/write coefficient access to matrices and arrays. |
453 | | * \ingroup Core_Module |
454 | | * \tparam Derived Type of the derived class |
455 | | * |
456 | | * \note #DirectWriteAccessors Constant indicating direct access |
457 | | * |
458 | | * This class defines functions to work with strides which can be used to access entries directly. This class |
459 | | * inherits DenseCoeffsBase<Derived, WriteAccessors> which defines functions to access entries read/write using |
460 | | * \c operator(). |
461 | | * |
462 | | * \sa \blank \ref TopicClassHierarchy |
463 | | */ |
464 | | template <typename Derived> |
465 | | class DenseCoeffsBase<Derived, DirectWriteAccessors> : public DenseCoeffsBase<Derived, WriteAccessors> { |
466 | | public: |
467 | | typedef DenseCoeffsBase<Derived, WriteAccessors> Base; |
468 | | typedef typename internal::traits<Derived>::Scalar Scalar; |
469 | | typedef typename NumTraits<Scalar>::Real RealScalar; |
470 | | |
471 | | using Base::cols; |
472 | | using Base::derived; |
473 | | using Base::rows; |
474 | | using Base::size; |
475 | | |
476 | | /** \returns the pointer increment between two consecutive elements within a slice in the inner direction. |
477 | | * |
478 | | * \sa outerStride(), rowStride(), colStride() |
479 | | */ |
480 | | EIGEN_DEVICE_FUNC EIGEN_CONSTEXPR inline Index innerStride() const EIGEN_NOEXCEPT { return derived().innerStride(); } |
481 | | |
482 | | /** \returns the pointer increment between two consecutive inner slices (for example, between two consecutive columns |
483 | | * in a column-major matrix). |
484 | | * |
485 | | * \sa innerStride(), rowStride(), colStride() |
486 | | */ |
487 | 18.6M | EIGEN_DEVICE_FUNC EIGEN_CONSTEXPR inline Index outerStride() const EIGEN_NOEXCEPT { return derived().outerStride(); } Eigen::DenseCoeffsBase<Eigen::Matrix<int, -1, -1, 0, -1, -1>, 3>::outerStride() const Line | Count | Source | 487 | 18.6M | EIGEN_DEVICE_FUNC EIGEN_CONSTEXPR inline Index outerStride() const EIGEN_NOEXCEPT { return derived().outerStride(); } |
Unexecuted instantiation: Eigen::DenseCoeffsBase<Eigen::Matrix<int, -1, 1, 0, -1, 1>, 3>::outerStride() const |
488 | | |
489 | | // FIXME shall we remove it ? |
490 | | EIGEN_CONSTEXPR inline Index stride() const EIGEN_NOEXCEPT { |
491 | | return Derived::IsVectorAtCompileTime ? innerStride() : outerStride(); |
492 | | } |
493 | | |
494 | | /** \returns the pointer increment between two consecutive rows. |
495 | | * |
496 | | * \sa innerStride(), outerStride(), colStride() |
497 | | */ |
498 | | EIGEN_DEVICE_FUNC EIGEN_CONSTEXPR inline Index rowStride() const EIGEN_NOEXCEPT { |
499 | | return Derived::IsRowMajor ? outerStride() : innerStride(); |
500 | | } |
501 | | |
502 | | /** \returns the pointer increment between two consecutive columns. |
503 | | * |
504 | | * \sa innerStride(), outerStride(), rowStride() |
505 | | */ |
506 | | EIGEN_DEVICE_FUNC EIGEN_CONSTEXPR inline Index colStride() const EIGEN_NOEXCEPT { |
507 | | return Derived::IsRowMajor ? innerStride() : outerStride(); |
508 | | } |
509 | | }; |
510 | | |
511 | | namespace internal { |
512 | | |
513 | | template <int Alignment, typename Derived, bool JustReturnZero> |
514 | | struct first_aligned_impl { |
515 | | static EIGEN_CONSTEXPR inline Index run(const Derived&) EIGEN_NOEXCEPT { return 0; } |
516 | | }; |
517 | | |
518 | | template <int Alignment, typename Derived> |
519 | | struct first_aligned_impl<Alignment, Derived, false> { |
520 | | static inline Index run(const Derived& m) { return internal::first_aligned<Alignment>(m.data(), m.size()); } |
521 | | }; |
522 | | |
523 | | /** \internal \returns the index of the first element of the array stored by \a m that is properly aligned with respect |
524 | | * to \a Alignment for vectorization. |
525 | | * |
526 | | * \tparam Alignment requested alignment in Bytes. |
527 | | * |
528 | | * There is also the variant first_aligned(const Scalar*, Integer) defined in Memory.h. See it for more |
529 | | * documentation. |
530 | | */ |
531 | | template <int Alignment, typename Derived> |
532 | | static inline Index first_aligned(const DenseBase<Derived>& m) { |
533 | | enum { ReturnZero = (int(evaluator<Derived>::Alignment) >= Alignment) || !(Derived::Flags & DirectAccessBit) }; |
534 | | return first_aligned_impl<Alignment, Derived, ReturnZero>::run(m.derived()); |
535 | | } |
536 | | |
537 | | template <typename Derived> |
538 | | static inline Index first_default_aligned(const DenseBase<Derived>& m) { |
539 | | typedef typename Derived::Scalar Scalar; |
540 | | typedef typename packet_traits<Scalar>::type DefaultPacketType; |
541 | | return internal::first_aligned<int(unpacket_traits<DefaultPacketType>::alignment), Derived>(m); |
542 | | } |
543 | | |
544 | | template <typename Derived, bool HasDirectAccess = has_direct_access<Derived>::ret> |
545 | | struct inner_stride_at_compile_time { |
546 | | enum { ret = traits<Derived>::InnerStrideAtCompileTime }; |
547 | | }; |
548 | | |
549 | | template <typename Derived> |
550 | | struct inner_stride_at_compile_time<Derived, false> { |
551 | | enum { ret = 0 }; |
552 | | }; |
553 | | |
554 | | template <typename Derived, bool HasDirectAccess = has_direct_access<Derived>::ret> |
555 | | struct outer_stride_at_compile_time { |
556 | | enum { ret = traits<Derived>::OuterStrideAtCompileTime }; |
557 | | }; |
558 | | |
559 | | template <typename Derived> |
560 | | struct outer_stride_at_compile_time<Derived, false> { |
561 | | enum { ret = 0 }; |
562 | | }; |
563 | | |
564 | | } // end namespace internal |
565 | | |
566 | | } // end namespace Eigen |
567 | | |
568 | | #endif // EIGEN_DENSECOEFFSBASE_H |