Home | History | Annotate | Download | only in Core
      1 // This file is part of Eigen, a lightweight C++ template library
      2 // for linear algebra.
      3 //
      4 // Copyright (C) 2009-2010 Gael Guennebaud <gael.guennebaud (at) 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 #ifndef EIGEN_ARRAYWRAPPER_H
     11 #define EIGEN_ARRAYWRAPPER_H
     12 
     13 namespace Eigen {
     14 
     15 /** \class ArrayWrapper
     16   * \ingroup Core_Module
     17   *
     18   * \brief Expression of a mathematical vector or matrix as an array object
     19   *
     20   * This class is the return type of MatrixBase::array(), and most of the time
     21   * this is the only way it is use.
     22   *
     23   * \sa MatrixBase::array(), class MatrixWrapper
     24   */
     25 
     26 namespace internal {
     27 template<typename ExpressionType>
     28 struct traits<ArrayWrapper<ExpressionType> >
     29   : public traits<typename remove_all<typename ExpressionType::Nested>::type >
     30 {
     31   typedef ArrayXpr XprKind;
     32 };
     33 }
     34 
     35 template<typename ExpressionType>
     36 class ArrayWrapper : public ArrayBase<ArrayWrapper<ExpressionType> >
     37 {
     38   public:
     39     typedef ArrayBase<ArrayWrapper> Base;
     40     EIGEN_DENSE_PUBLIC_INTERFACE(ArrayWrapper)
     41     EIGEN_INHERIT_ASSIGNMENT_OPERATORS(ArrayWrapper)
     42 
     43     typedef typename internal::conditional<
     44                        internal::is_lvalue<ExpressionType>::value,
     45                        Scalar,
     46                        const Scalar
     47                      >::type ScalarWithConstIfNotLvalue;
     48 
     49     typedef typename internal::nested<ExpressionType>::type NestedExpressionType;
     50 
     51     inline ArrayWrapper(ExpressionType& matrix) : m_expression(matrix) {}
     52 
     53     inline Index rows() const { return m_expression.rows(); }
     54     inline Index cols() const { return m_expression.cols(); }
     55     inline Index outerStride() const { return m_expression.outerStride(); }
     56     inline Index innerStride() const { return m_expression.innerStride(); }
     57 
     58     inline ScalarWithConstIfNotLvalue* data() { return m_expression.data(); }
     59     inline const Scalar* data() const { return m_expression.data(); }
     60 
     61     inline CoeffReturnType coeff(Index row, Index col) const
     62     {
     63       return m_expression.coeff(row, col);
     64     }
     65 
     66     inline Scalar& coeffRef(Index row, Index col)
     67     {
     68       return m_expression.const_cast_derived().coeffRef(row, col);
     69     }
     70 
     71     inline const Scalar& coeffRef(Index row, Index col) const
     72     {
     73       return m_expression.const_cast_derived().coeffRef(row, col);
     74     }
     75 
     76     inline CoeffReturnType coeff(Index index) const
     77     {
     78       return m_expression.coeff(index);
     79     }
     80 
     81     inline Scalar& coeffRef(Index index)
     82     {
     83       return m_expression.const_cast_derived().coeffRef(index);
     84     }
     85 
     86     inline const Scalar& coeffRef(Index index) const
     87     {
     88       return m_expression.const_cast_derived().coeffRef(index);
     89     }
     90 
     91     template<int LoadMode>
     92     inline const PacketScalar packet(Index row, Index col) const
     93     {
     94       return m_expression.template packet<LoadMode>(row, col);
     95     }
     96 
     97     template<int LoadMode>
     98     inline void writePacket(Index row, Index col, const PacketScalar& x)
     99     {
    100       m_expression.const_cast_derived().template writePacket<LoadMode>(row, col, x);
    101     }
    102 
    103     template<int LoadMode>
    104     inline const PacketScalar packet(Index index) const
    105     {
    106       return m_expression.template packet<LoadMode>(index);
    107     }
    108 
    109     template<int LoadMode>
    110     inline void writePacket(Index index, const PacketScalar& x)
    111     {
    112       m_expression.const_cast_derived().template writePacket<LoadMode>(index, x);
    113     }
    114 
    115     template<typename Dest>
    116     inline void evalTo(Dest& dst) const { dst = m_expression; }
    117 
    118     const typename internal::remove_all<NestedExpressionType>::type&
    119     nestedExpression() const
    120     {
    121       return m_expression;
    122     }
    123 
    124   protected:
    125     NestedExpressionType m_expression;
    126 };
    127 
    128 /** \class MatrixWrapper
    129   * \ingroup Core_Module
    130   *
    131   * \brief Expression of an array as a mathematical vector or matrix
    132   *
    133   * This class is the return type of ArrayBase::matrix(), and most of the time
    134   * this is the only way it is use.
    135   *
    136   * \sa MatrixBase::matrix(), class ArrayWrapper
    137   */
    138 
    139 namespace internal {
    140 template<typename ExpressionType>
    141 struct traits<MatrixWrapper<ExpressionType> >
    142  : public traits<typename remove_all<typename ExpressionType::Nested>::type >
    143 {
    144   typedef MatrixXpr XprKind;
    145 };
    146 }
    147 
    148 template<typename ExpressionType>
    149 class MatrixWrapper : public MatrixBase<MatrixWrapper<ExpressionType> >
    150 {
    151   public:
    152     typedef MatrixBase<MatrixWrapper<ExpressionType> > Base;
    153     EIGEN_DENSE_PUBLIC_INTERFACE(MatrixWrapper)
    154     EIGEN_INHERIT_ASSIGNMENT_OPERATORS(MatrixWrapper)
    155 
    156     typedef typename internal::conditional<
    157                        internal::is_lvalue<ExpressionType>::value,
    158                        Scalar,
    159                        const Scalar
    160                      >::type ScalarWithConstIfNotLvalue;
    161 
    162     typedef typename internal::nested<ExpressionType>::type NestedExpressionType;
    163 
    164     inline MatrixWrapper(ExpressionType& matrix) : m_expression(matrix) {}
    165 
    166     inline Index rows() const { return m_expression.rows(); }
    167     inline Index cols() const { return m_expression.cols(); }
    168     inline Index outerStride() const { return m_expression.outerStride(); }
    169     inline Index innerStride() const { return m_expression.innerStride(); }
    170 
    171     inline ScalarWithConstIfNotLvalue* data() { return m_expression.data(); }
    172     inline const Scalar* data() const { return m_expression.data(); }
    173 
    174     inline CoeffReturnType coeff(Index row, Index col) const
    175     {
    176       return m_expression.coeff(row, col);
    177     }
    178 
    179     inline Scalar& coeffRef(Index row, Index col)
    180     {
    181       return m_expression.const_cast_derived().coeffRef(row, col);
    182     }
    183 
    184     inline const Scalar& coeffRef(Index row, Index col) const
    185     {
    186       return m_expression.derived().coeffRef(row, col);
    187     }
    188 
    189     inline CoeffReturnType coeff(Index index) const
    190     {
    191       return m_expression.coeff(index);
    192     }
    193 
    194     inline Scalar& coeffRef(Index index)
    195     {
    196       return m_expression.const_cast_derived().coeffRef(index);
    197     }
    198 
    199     inline const Scalar& coeffRef(Index index) const
    200     {
    201       return m_expression.const_cast_derived().coeffRef(index);
    202     }
    203 
    204     template<int LoadMode>
    205     inline const PacketScalar packet(Index row, Index col) const
    206     {
    207       return m_expression.template packet<LoadMode>(row, col);
    208     }
    209 
    210     template<int LoadMode>
    211     inline void writePacket(Index row, Index col, const PacketScalar& x)
    212     {
    213       m_expression.const_cast_derived().template writePacket<LoadMode>(row, col, x);
    214     }
    215 
    216     template<int LoadMode>
    217     inline const PacketScalar packet(Index index) const
    218     {
    219       return m_expression.template packet<LoadMode>(index);
    220     }
    221 
    222     template<int LoadMode>
    223     inline void writePacket(Index index, const PacketScalar& x)
    224     {
    225       m_expression.const_cast_derived().template writePacket<LoadMode>(index, x);
    226     }
    227 
    228     const typename internal::remove_all<NestedExpressionType>::type&
    229     nestedExpression() const
    230     {
    231       return m_expression;
    232     }
    233 
    234   protected:
    235     NestedExpressionType m_expression;
    236 };
    237 
    238 } // end namespace Eigen
    239 
    240 #endif // EIGEN_ARRAYWRAPPER_H
    241