Branch data Line data Source code
1 : : // This file is part of Eigen, a lightweight C++ template library
2 : : // for linear algebra.
3 : : //
4 : : // Copyright (C) 2008 Gael Guennebaud <gael.guennebaud@inria.fr>
5 : : // Copyright (C) 2006-2010 Benoit Jacob <jacob.benoit.1@gmail.com>
6 : : //
7 : : // This Source Code Form is subject to the terms of the Mozilla
8 : : // Public License v. 2.0. If a copy of the MPL was not distributed
9 : : // with this file, You can obtain one at http://mozilla.org/MPL/2.0/.
10 : :
11 : : #ifndef EIGEN_BLOCK_H
12 : : #define EIGEN_BLOCK_H
13 : :
14 : : namespace Eigen {
15 : :
16 : : namespace internal {
17 : : template<typename XprType, int BlockRows, int BlockCols, bool InnerPanel>
18 : : struct traits<Block<XprType, BlockRows, BlockCols, InnerPanel> > : traits<XprType>
19 : : {
20 : : typedef typename traits<XprType>::Scalar Scalar;
21 : : typedef typename traits<XprType>::StorageKind StorageKind;
22 : : typedef typename traits<XprType>::XprKind XprKind;
23 : : typedef typename ref_selector<XprType>::type XprTypeNested;
24 : : typedef typename remove_reference<XprTypeNested>::type _XprTypeNested;
25 : : enum{
26 : : MatrixRows = traits<XprType>::RowsAtCompileTime,
27 : : MatrixCols = traits<XprType>::ColsAtCompileTime,
28 : : RowsAtCompileTime = MatrixRows == 0 ? 0 : BlockRows,
29 : : ColsAtCompileTime = MatrixCols == 0 ? 0 : BlockCols,
30 : : MaxRowsAtCompileTime = BlockRows==0 ? 0
31 : : : RowsAtCompileTime != Dynamic ? int(RowsAtCompileTime)
32 : : : int(traits<XprType>::MaxRowsAtCompileTime),
33 : : MaxColsAtCompileTime = BlockCols==0 ? 0
34 : : : ColsAtCompileTime != Dynamic ? int(ColsAtCompileTime)
35 : : : int(traits<XprType>::MaxColsAtCompileTime),
36 : :
37 : : XprTypeIsRowMajor = (int(traits<XprType>::Flags)&RowMajorBit) != 0,
38 : : IsRowMajor = (MaxRowsAtCompileTime==1&&MaxColsAtCompileTime!=1) ? 1
39 : : : (MaxColsAtCompileTime==1&&MaxRowsAtCompileTime!=1) ? 0
40 : : : XprTypeIsRowMajor,
41 : : HasSameStorageOrderAsXprType = (IsRowMajor == XprTypeIsRowMajor),
42 : : InnerSize = IsRowMajor ? int(ColsAtCompileTime) : int(RowsAtCompileTime),
43 : : InnerStrideAtCompileTime = HasSameStorageOrderAsXprType
44 : : ? int(inner_stride_at_compile_time<XprType>::ret)
45 : : : int(outer_stride_at_compile_time<XprType>::ret),
46 : : OuterStrideAtCompileTime = HasSameStorageOrderAsXprType
47 : : ? int(outer_stride_at_compile_time<XprType>::ret)
48 : : : int(inner_stride_at_compile_time<XprType>::ret),
49 : :
50 : : // FIXME, this traits is rather specialized for dense object and it needs to be cleaned further
51 : : FlagsLvalueBit = is_lvalue<XprType>::value ? LvalueBit : 0,
52 : : FlagsRowMajorBit = IsRowMajor ? RowMajorBit : 0,
53 : : Flags = (traits<XprType>::Flags & (DirectAccessBit | (InnerPanel?CompressedAccessBit:0))) | FlagsLvalueBit | FlagsRowMajorBit,
54 : : // FIXME DirectAccessBit should not be handled by expressions
55 : : //
56 : : // Alignment is needed by MapBase's assertions
57 : : // We can sefely set it to false here. Internal alignment errors will be detected by an eigen_internal_assert in the respective evaluator
58 : : Alignment = 0
59 : : };
60 : : };
61 : :
62 : : template<typename XprType, int BlockRows=Dynamic, int BlockCols=Dynamic, bool InnerPanel = false,
63 : : bool HasDirectAccess = internal::has_direct_access<XprType>::ret> class BlockImpl_dense;
64 : :
65 : : } // end namespace internal
66 : :
67 : : template<typename XprType, int BlockRows, int BlockCols, bool InnerPanel, typename StorageKind> class BlockImpl;
68 : :
69 : : /** \class Block
70 : : * \ingroup Core_Module
71 : : *
72 : : * \brief Expression of a fixed-size or dynamic-size block
73 : : *
74 : : * \tparam XprType the type of the expression in which we are taking a block
75 : : * \tparam BlockRows the number of rows of the block we are taking at compile time (optional)
76 : : * \tparam BlockCols the number of columns of the block we are taking at compile time (optional)
77 : : * \tparam InnerPanel is true, if the block maps to a set of rows of a row major matrix or
78 : : * to set of columns of a column major matrix (optional). The parameter allows to determine
79 : : * at compile time whether aligned access is possible on the block expression.
80 : : *
81 : : * This class represents an expression of either a fixed-size or dynamic-size block. It is the return
82 : : * type of DenseBase::block(Index,Index,Index,Index) and DenseBase::block<int,int>(Index,Index) and
83 : : * most of the time this is the only way it is used.
84 : : *
85 : : * However, if you want to directly maniputate block expressions,
86 : : * for instance if you want to write a function returning such an expression, you
87 : : * will need to use this class.
88 : : *
89 : : * Here is an example illustrating the dynamic case:
90 : : * \include class_Block.cpp
91 : : * Output: \verbinclude class_Block.out
92 : : *
93 : : * \note Even though this expression has dynamic size, in the case where \a XprType
94 : : * has fixed size, this expression inherits a fixed maximal size which means that evaluating
95 : : * it does not cause a dynamic memory allocation.
96 : : *
97 : : * Here is an example illustrating the fixed-size case:
98 : : * \include class_FixedBlock.cpp
99 : : * Output: \verbinclude class_FixedBlock.out
100 : : *
101 : : * \sa DenseBase::block(Index,Index,Index,Index), DenseBase::block(Index,Index), class VectorBlock
102 : : */
103 : : template<typename XprType, int BlockRows, int BlockCols, bool InnerPanel> class Block
104 : : : public BlockImpl<XprType, BlockRows, BlockCols, InnerPanel, typename internal::traits<XprType>::StorageKind>
105 : : {
106 : : typedef BlockImpl<XprType, BlockRows, BlockCols, InnerPanel, typename internal::traits<XprType>::StorageKind> Impl;
107 : : public:
108 : : //typedef typename Impl::Base Base;
109 : : typedef Impl Base;
110 : : EIGEN_GENERIC_PUBLIC_INTERFACE(Block)
111 : 3801 : EIGEN_INHERIT_ASSIGNMENT_OPERATORS(Block)
112 : :
113 : : typedef typename internal::remove_all<XprType>::type NestedExpression;
114 : :
115 : : /** Column or Row constructor
116 : : */
117 : : EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE
118 : 6260 : Block(XprType& xpr, Index i) : Impl(xpr,i)
119 : : {
120 : 6260 : eigen_assert( (i>=0) && (
121 : : ((BlockRows==1) && (BlockCols==XprType::ColsAtCompileTime) && i<xpr.rows())
122 : : ||((BlockRows==XprType::RowsAtCompileTime) && (BlockCols==1) && i<xpr.cols())));
123 : 6260 : }
124 : :
125 : : /** Fixed-size constructor
126 : : */
127 : : EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE
128 : 9374 : Block(XprType& xpr, Index startRow, Index startCol)
129 : 9374 : : Impl(xpr, startRow, startCol)
130 : : {
131 : : EIGEN_STATIC_ASSERT(RowsAtCompileTime!=Dynamic && ColsAtCompileTime!=Dynamic,THIS_METHOD_IS_ONLY_FOR_FIXED_SIZE)
132 : 9374 : eigen_assert(startRow >= 0 && BlockRows >= 0 && startRow + BlockRows <= xpr.rows()
133 : : && startCol >= 0 && BlockCols >= 0 && startCol + BlockCols <= xpr.cols());
134 : 9374 : }
135 : :
136 : : /** Dynamic-size constructor
137 : : */
138 : : EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE
139 : 2612 : Block(XprType& xpr,
140 : : Index startRow, Index startCol,
141 : : Index blockRows, Index blockCols)
142 : 2612 : : Impl(xpr, startRow, startCol, blockRows, blockCols)
143 : : {
144 : 2306 : eigen_assert((RowsAtCompileTime==Dynamic || RowsAtCompileTime==blockRows)
145 : : && (ColsAtCompileTime==Dynamic || ColsAtCompileTime==blockCols));
146 : 2612 : eigen_assert(startRow >= 0 && blockRows >= 0 && startRow <= xpr.rows() - blockRows
147 : : && startCol >= 0 && blockCols >= 0 && startCol <= xpr.cols() - blockCols);
148 : 2612 : }
149 : : };
150 : :
151 : : // The generic default implementation for dense block simplu forward to the internal::BlockImpl_dense
152 : : // that must be specialized for direct and non-direct access...
153 : : template<typename XprType, int BlockRows, int BlockCols, bool InnerPanel>
154 : : class BlockImpl<XprType, BlockRows, BlockCols, InnerPanel, Dense>
155 : : : public internal::BlockImpl_dense<XprType, BlockRows, BlockCols, InnerPanel>
156 : : {
157 : : typedef internal::BlockImpl_dense<XprType, BlockRows, BlockCols, InnerPanel> Impl;
158 : : typedef typename XprType::StorageIndex StorageIndex;
159 : : public:
160 : : typedef Impl Base;
161 : 3801 : EIGEN_INHERIT_ASSIGNMENT_OPERATORS(BlockImpl)
162 : 6260 : EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE BlockImpl(XprType& xpr, Index i) : Impl(xpr,i) {}
163 : 9374 : EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE BlockImpl(XprType& xpr, Index startRow, Index startCol) : Impl(xpr, startRow, startCol) {}
164 : : EIGEN_DEVICE_FUNC
165 : 2612 : EIGEN_STRONG_INLINE BlockImpl(XprType& xpr, Index startRow, Index startCol, Index blockRows, Index blockCols)
166 : 2612 : : Impl(xpr, startRow, startCol, blockRows, blockCols) {}
167 : : };
168 : :
169 : : namespace internal {
170 : :
171 : : /** \internal Internal implementation of dense Blocks in the general case. */
172 : : template<typename XprType, int BlockRows, int BlockCols, bool InnerPanel, bool HasDirectAccess> class BlockImpl_dense
173 : : : public internal::dense_xpr_base<Block<XprType, BlockRows, BlockCols, InnerPanel> >::type
174 : : {
175 : : typedef Block<XprType, BlockRows, BlockCols, InnerPanel> BlockType;
176 : : typedef typename internal::ref_selector<XprType>::non_const_type XprTypeNested;
177 : : public:
178 : :
179 : : typedef typename internal::dense_xpr_base<BlockType>::type Base;
180 : : EIGEN_DENSE_PUBLIC_INTERFACE(BlockType)
181 : 3648 : EIGEN_INHERIT_ASSIGNMENT_OPERATORS(BlockImpl_dense)
182 : :
183 : : // class InnerIterator; // FIXME apparently never used
184 : :
185 : : /** Column or Row constructor
186 : : */
187 : : EIGEN_DEVICE_FUNC
188 : 1824 : inline BlockImpl_dense(XprType& xpr, Index i)
189 : 1824 : : m_xpr(xpr),
190 : : // It is a row if and only if BlockRows==1 and BlockCols==XprType::ColsAtCompileTime,
191 : : // and it is a column if and only if BlockRows==XprType::RowsAtCompileTime and BlockCols==1,
192 : : // all other cases are invalid.
193 : : // The case a 1x1 matrix seems ambiguous, but the result is the same anyway.
194 : 1824 : m_startRow( (BlockRows==1) && (BlockCols==XprType::ColsAtCompileTime) ? i : 0),
195 : 1824 : m_startCol( (BlockRows==XprType::RowsAtCompileTime) && (BlockCols==1) ? i : 0),
196 : 1824 : m_blockRows(BlockRows==1 ? 1 : xpr.rows()),
197 : 3648 : m_blockCols(BlockCols==1 ? 1 : xpr.cols())
198 : 1824 : {}
199 : :
200 : : /** Fixed-size constructor
201 : : */
202 : : EIGEN_DEVICE_FUNC
203 : : inline BlockImpl_dense(XprType& xpr, Index startRow, Index startCol)
204 : : : m_xpr(xpr), m_startRow(startRow), m_startCol(startCol),
205 : : m_blockRows(BlockRows), m_blockCols(BlockCols)
206 : : {}
207 : :
208 : : /** Dynamic-size constructor
209 : : */
210 : : EIGEN_DEVICE_FUNC
211 : : inline BlockImpl_dense(XprType& xpr,
212 : : Index startRow, Index startCol,
213 : : Index blockRows, Index blockCols)
214 : : : m_xpr(xpr), m_startRow(startRow), m_startCol(startCol),
215 : : m_blockRows(blockRows), m_blockCols(blockCols)
216 : : {}
217 : :
218 : 5016 : EIGEN_DEVICE_FUNC inline Index rows() const { return m_blockRows.value(); }
219 : 5016 : EIGEN_DEVICE_FUNC inline Index cols() const { return m_blockCols.value(); }
220 : :
221 : : EIGEN_DEVICE_FUNC
222 : : inline Scalar& coeffRef(Index rowId, Index colId)
223 : : {
224 : : EIGEN_STATIC_ASSERT_LVALUE(XprType)
225 : : return m_xpr.coeffRef(rowId + m_startRow.value(), colId + m_startCol.value());
226 : : }
227 : :
228 : : EIGEN_DEVICE_FUNC
229 : : inline const Scalar& coeffRef(Index rowId, Index colId) const
230 : : {
231 : : return m_xpr.derived().coeffRef(rowId + m_startRow.value(), colId + m_startCol.value());
232 : : }
233 : :
234 : : EIGEN_DEVICE_FUNC
235 : : EIGEN_STRONG_INLINE const CoeffReturnType coeff(Index rowId, Index colId) const
236 : : {
237 : : return m_xpr.coeff(rowId + m_startRow.value(), colId + m_startCol.value());
238 : : }
239 : :
240 : : EIGEN_DEVICE_FUNC
241 : : inline Scalar& coeffRef(Index index)
242 : : {
243 : : EIGEN_STATIC_ASSERT_LVALUE(XprType)
244 : : return m_xpr.coeffRef(m_startRow.value() + (RowsAtCompileTime == 1 ? 0 : index),
245 : : m_startCol.value() + (RowsAtCompileTime == 1 ? index : 0));
246 : : }
247 : :
248 : : EIGEN_DEVICE_FUNC
249 : : inline const Scalar& coeffRef(Index index) const
250 : : {
251 : : return m_xpr.coeffRef(m_startRow.value() + (RowsAtCompileTime == 1 ? 0 : index),
252 : : m_startCol.value() + (RowsAtCompileTime == 1 ? index : 0));
253 : : }
254 : :
255 : : EIGEN_DEVICE_FUNC
256 : : inline const CoeffReturnType coeff(Index index) const
257 : : {
258 : : return m_xpr.coeff(m_startRow.value() + (RowsAtCompileTime == 1 ? 0 : index),
259 : : m_startCol.value() + (RowsAtCompileTime == 1 ? index : 0));
260 : : }
261 : :
262 : : template<int LoadMode>
263 : : inline PacketScalar packet(Index rowId, Index colId) const
264 : : {
265 : : return m_xpr.template packet<Unaligned>(rowId + m_startRow.value(), colId + m_startCol.value());
266 : : }
267 : :
268 : : template<int LoadMode>
269 : : inline void writePacket(Index rowId, Index colId, const PacketScalar& val)
270 : : {
271 : : m_xpr.template writePacket<Unaligned>(rowId + m_startRow.value(), colId + m_startCol.value(), val);
272 : : }
273 : :
274 : : template<int LoadMode>
275 : : inline PacketScalar packet(Index index) const
276 : : {
277 : : return m_xpr.template packet<Unaligned>
278 : : (m_startRow.value() + (RowsAtCompileTime == 1 ? 0 : index),
279 : : m_startCol.value() + (RowsAtCompileTime == 1 ? index : 0));
280 : : }
281 : :
282 : : template<int LoadMode>
283 : : inline void writePacket(Index index, const PacketScalar& val)
284 : : {
285 : : m_xpr.template writePacket<Unaligned>
286 : : (m_startRow.value() + (RowsAtCompileTime == 1 ? 0 : index),
287 : : m_startCol.value() + (RowsAtCompileTime == 1 ? index : 0), val);
288 : : }
289 : :
290 : : #ifdef EIGEN_PARSED_BY_DOXYGEN
291 : : /** \sa MapBase::data() */
292 : : EIGEN_DEVICE_FUNC inline const Scalar* data() const;
293 : : EIGEN_DEVICE_FUNC inline Index innerStride() const;
294 : : EIGEN_DEVICE_FUNC inline Index outerStride() const;
295 : : #endif
296 : :
297 : : EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE
298 : 3192 : const typename internal::remove_all<XprTypeNested>::type& nestedExpression() const
299 : : {
300 : 3192 : return m_xpr;
301 : : }
302 : :
303 : : EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE
304 : : XprType& nestedExpression() { return m_xpr; }
305 : :
306 : : EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE EIGEN_CONSTEXPR
307 : 3192 : StorageIndex startRow() const EIGEN_NOEXCEPT
308 : : {
309 : 3192 : return m_startRow.value();
310 : : }
311 : :
312 : : EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE EIGEN_CONSTEXPR
313 : 3192 : StorageIndex startCol() const EIGEN_NOEXCEPT
314 : : {
315 : 3192 : return m_startCol.value();
316 : : }
317 : :
318 : : protected:
319 : :
320 : : XprTypeNested m_xpr;
321 : : const internal::variable_if_dynamic<StorageIndex, (XprType::RowsAtCompileTime == 1 && BlockRows==1) ? 0 : Dynamic> m_startRow;
322 : : const internal::variable_if_dynamic<StorageIndex, (XprType::ColsAtCompileTime == 1 && BlockCols==1) ? 0 : Dynamic> m_startCol;
323 : : const internal::variable_if_dynamic<StorageIndex, RowsAtCompileTime> m_blockRows;
324 : : const internal::variable_if_dynamic<StorageIndex, ColsAtCompileTime> m_blockCols;
325 : : };
326 : :
327 : : /** \internal Internal implementation of dense Blocks in the direct access case.*/
328 : : template<typename XprType, int BlockRows, int BlockCols, bool InnerPanel>
329 : : class BlockImpl_dense<XprType,BlockRows,BlockCols, InnerPanel,true>
330 : : : public MapBase<Block<XprType, BlockRows, BlockCols, InnerPanel> >
331 : : {
332 : : typedef Block<XprType, BlockRows, BlockCols, InnerPanel> BlockType;
333 : : typedef typename internal::ref_selector<XprType>::non_const_type XprTypeNested;
334 : : enum {
335 : : XprTypeIsRowMajor = (int(traits<XprType>::Flags)&RowMajorBit) != 0
336 : : };
337 : : public:
338 : :
339 : : typedef MapBase<BlockType> Base;
340 : : EIGEN_DENSE_PUBLIC_INTERFACE(BlockType)
341 : 153 : EIGEN_INHERIT_ASSIGNMENT_OPERATORS(BlockImpl_dense)
342 : :
343 : : /** Column or Row constructor
344 : : */
345 : : EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE
346 : 4436 : BlockImpl_dense(XprType& xpr, Index i)
347 : 5804 : : Base(xpr.data() + i * ( ((BlockRows==1) && (BlockCols==XprType::ColsAtCompileTime) && (!XprTypeIsRowMajor))
348 : 4436 : || ((BlockRows==XprType::RowsAtCompileTime) && (BlockCols==1) && ( XprTypeIsRowMajor)) ? xpr.innerStride() : xpr.outerStride()),
349 : : BlockRows==1 ? 1 : xpr.rows(),
350 : : BlockCols==1 ? 1 : xpr.cols()),
351 : 4436 : m_xpr(xpr),
352 : 4436 : m_startRow( (BlockRows==1) && (BlockCols==XprType::ColsAtCompileTime) ? i : 0),
353 : 13308 : m_startCol( (BlockRows==XprType::RowsAtCompileTime) && (BlockCols==1) ? i : 0)
354 : : {
355 : 4436 : init();
356 : 4436 : }
357 : :
358 : : /** Fixed-size constructor
359 : : */
360 : : EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE
361 : 9374 : BlockImpl_dense(XprType& xpr, Index startRow, Index startCol)
362 : 9374 : : Base(xpr.data()+xpr.innerStride()*(XprTypeIsRowMajor?startCol:startRow) + xpr.outerStride()*(XprTypeIsRowMajor?startRow:startCol)),
363 : 18748 : m_xpr(xpr), m_startRow(startRow), m_startCol(startCol)
364 : : {
365 : 9374 : init();
366 : 9374 : }
367 : :
368 : : /** Dynamic-size constructor
369 : : */
370 : : EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE
371 : 2612 : BlockImpl_dense(XprType& xpr,
372 : : Index startRow, Index startCol,
373 : : Index blockRows, Index blockCols)
374 : 2612 : : Base(xpr.data()+xpr.innerStride()*(XprTypeIsRowMajor?startCol:startRow) + xpr.outerStride()*(XprTypeIsRowMajor?startRow:startCol), blockRows, blockCols),
375 : 5224 : m_xpr(xpr), m_startRow(startRow), m_startCol(startCol)
376 : : {
377 : 2612 : init();
378 : 2612 : }
379 : :
380 : : EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE
381 : : const typename internal::remove_all<XprTypeNested>::type& nestedExpression() const EIGEN_NOEXCEPT
382 : : {
383 : : return m_xpr;
384 : : }
385 : :
386 : : EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE
387 : : XprType& nestedExpression() { return m_xpr; }
388 : :
389 : : /** \sa MapBase::innerStride() */
390 : : EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE EIGEN_CONSTEXPR
391 : 26422 : Index innerStride() const EIGEN_NOEXCEPT
392 : : {
393 : : return internal::traits<BlockType>::HasSameStorageOrderAsXprType
394 : 26422 : ? m_xpr.innerStride()
395 : 26422 : : m_xpr.outerStride();
396 : : }
397 : :
398 : : /** \sa MapBase::outerStride() */
399 : : EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE EIGEN_CONSTEXPR
400 : 14728 : Index outerStride() const EIGEN_NOEXCEPT
401 : : {
402 : : return internal::traits<BlockType>::HasSameStorageOrderAsXprType
403 : 14728 : ? m_xpr.outerStride()
404 : 14728 : : m_xpr.innerStride();
405 : : }
406 : :
407 : : EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE EIGEN_CONSTEXPR
408 : : StorageIndex startRow() const EIGEN_NOEXCEPT { return m_startRow.value(); }
409 : :
410 : : EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE EIGEN_CONSTEXPR
411 : : StorageIndex startCol() const EIGEN_NOEXCEPT { return m_startCol.value(); }
412 : :
413 : : #ifndef __SUNPRO_CC
414 : : // FIXME sunstudio is not friendly with the above friend...
415 : : // META-FIXME there is no 'friend' keyword around here. Is this obsolete?
416 : : protected:
417 : : #endif
418 : :
419 : : #ifndef EIGEN_PARSED_BY_DOXYGEN
420 : : /** \internal used by allowAligned() */
421 : : EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE
422 : : BlockImpl_dense(XprType& xpr, const Scalar* data, Index blockRows, Index blockCols)
423 : : : Base(data, blockRows, blockCols), m_xpr(xpr)
424 : : {
425 : : init();
426 : : }
427 : : #endif
428 : :
429 : : protected:
430 : : EIGEN_DEVICE_FUNC EIGEN_STRONG_INLINE
431 : 16422 : void init()
432 : : {
433 : 16422 : m_outerStride = internal::traits<BlockType>::HasSameStorageOrderAsXprType
434 : 16422 : ? m_xpr.outerStride()
435 : 1306 : : m_xpr.innerStride();
436 : 16422 : }
437 : :
438 : : XprTypeNested m_xpr;
439 : : const internal::variable_if_dynamic<StorageIndex, (XprType::RowsAtCompileTime == 1 && BlockRows==1) ? 0 : Dynamic> m_startRow;
440 : : const internal::variable_if_dynamic<StorageIndex, (XprType::ColsAtCompileTime == 1 && BlockCols==1) ? 0 : Dynamic> m_startCol;
441 : : Index m_outerStride;
442 : : };
443 : :
444 : : } // end namespace internal
445 : :
446 : : } // end namespace Eigen
447 : :
448 : : #endif // EIGEN_BLOCK_H
|