From bae2e3327b27a21e5024e235255f403cfe1be2c5 Mon Sep 17 00:00:00 2001 From: Gael Guennebaud Date: Thu, 31 Jul 2014 13:35:49 +0200 Subject: Call product_generic_impl by default, and remove lot of boilerplate code --- Eigen/src/Geometry/Homogeneous.h | 175 ++++++++++++++++++++++++++++++++++++++- Eigen/src/Geometry/Transform.h | 22 +++++ 2 files changed, 195 insertions(+), 2 deletions(-) (limited to 'Eigen/src/Geometry') diff --git a/Eigen/src/Geometry/Homogeneous.h b/Eigen/src/Geometry/Homogeneous.h index 00e71d190..07bc22154 100644 --- a/Eigen/src/Geometry/Homogeneous.h +++ b/Eigen/src/Geometry/Homogeneous.h @@ -48,8 +48,10 @@ struct traits > TmpFlags = _MatrixTypeNested::Flags & HereditaryBits, Flags = ColsAtCompileTime==1 ? (TmpFlags & ~RowMajorBit) : RowsAtCompileTime==1 ? (TmpFlags | RowMajorBit) - : TmpFlags, - CoeffReadCost = _MatrixTypeNested::CoeffReadCost + : TmpFlags +#ifndef EIGEN_TEST_EVALUATORS + , CoeffReadCost = _MatrixTypeNested::CoeffReadCost +#endif // EIGEN_TEST_EVALUATORS }; }; @@ -63,6 +65,7 @@ template class Homogeneous { public: + typedef MatrixType NestedExpression; enum { Direction = _Direction }; typedef MatrixBase Base; @@ -74,7 +77,10 @@ template class Homogeneous inline Index rows() const { return m_matrix.rows() + (int(Direction)==Vertical ? 1 : 0); } inline Index cols() const { return m_matrix.cols() + (int(Direction)==Horizontal ? 1 : 0); } + + const NestedExpression& nestedExpression() const { return m_matrix; } +#ifndef EIGEN_TEST_EVALUATORS inline Scalar coeff(Index row, Index col) const { if( (int(Direction)==Vertical && row==m_matrix.rows()) @@ -106,6 +112,31 @@ template class Homogeneous eigen_assert(int(Direction)==Vertical); return internal::homogeneous_left_product_impl >(lhs,rhs.m_matrix); } +#else + template + inline const Product + operator* (const MatrixBase& rhs) const + { + eigen_assert(int(Direction)==Horizontal); + return Product(*this,rhs.derived()); + } + + template friend + inline const Product + operator* (const MatrixBase& lhs, const Homogeneous& rhs) + { + eigen_assert(int(Direction)==Vertical); + return Product(lhs.derived(),rhs); + } + + template friend + inline const Product, Homogeneous > + operator* (const Transform& lhs, const Homogeneous& rhs) + { + eigen_assert(int(Direction)==Vertical); + return Product, Homogeneous>(lhs,rhs); + } +#endif protected: typename MatrixType::Nested m_matrix; @@ -300,6 +331,146 @@ struct homogeneous_right_product_impl,Rhs> typename Rhs::Nested m_rhs; }; +#ifdef EIGEN_TEST_EVALUATORS +template +struct unary_evaluator, IndexBased> + : evaluator::PlainObject >::type +{ + typedef Homogeneous XprType; + typedef typename XprType::PlainObject PlainObject; + typedef typename evaluator::type Base; + + unary_evaluator(const XprType& op) + : Base(), m_temp(op) + { + ::new (static_cast(this)) Base(m_temp); + } + +protected: + PlainObject m_temp; +}; + +// dense = homogeneous +template< typename DstXprType, typename ArgType, typename Scalar> +struct Assignment, internal::assign_op, Dense2Dense, Scalar> +{ + typedef Homogeneous SrcXprType; + static void run(DstXprType &dst, const SrcXprType &src, const internal::assign_op &) + { + dst.template topRows(src.nestedExpression().rows()) = src.nestedExpression(); +// dst.topRows(src.nestedExpression().rows()) = src.nestedExpression(); + dst.row(dst.rows()-1).setOnes(); + } +}; + +// dense = homogeneous +template< typename DstXprType, typename ArgType, typename Scalar> +struct Assignment, internal::assign_op, Dense2Dense, Scalar> +{ + typedef Homogeneous SrcXprType; + static void run(DstXprType &dst, const SrcXprType &src, const internal::assign_op &) + { + dst.template leftCols(src.nestedExpression().cols()) = src.nestedExpression(); +// dst.leftCols(src.nestedExpression().cols()) = src.nestedExpression(); + dst.col(dst.cols()-1).setOnes(); + } +}; + +template +struct generic_product_impl, Rhs, DenseShape, DenseShape, ProductTag> +{ + template + static void evalTo(Dest& dst, const Homogeneous& lhs, const Rhs& rhs) + { + homogeneous_right_product_impl, Rhs>(lhs.nestedExpression(), rhs).evalTo(dst); + } +}; + +template +struct generic_product_impl, DenseShape, DenseShape, ProductTag> +{ + template + static void evalTo(Dest& dst, const Lhs& lhs, const Homogeneous& rhs) + { + homogeneous_left_product_impl, Lhs>(rhs.nestedExpression(), lhs).evalTo(dst); + } +}; + +template +struct generic_product_impl, Homogeneous, DenseShape, DenseShape, ProductTag> +{ + typedef Transform TransformType; + template + static void evalTo(Dest& dst, const TransformType& lhs, const Homogeneous& rhs) + { + homogeneous_left_product_impl, TransformType>(rhs.nestedExpression(), lhs).evalTo(dst); + } +}; + + +template +struct product_evaluator, Rhs, DefaultProduct>, ProductTag, DenseShape, DenseShape, typename traits::Scalar, typename traits::Scalar> + : public evaluator, Rhs, DefaultProduct>::PlainObject>::type +{ + typedef Homogeneous Lhs; + typedef Product XprType; + typedef typename XprType::PlainObject PlainObject; + typedef typename evaluator::type Base; + + product_evaluator(const XprType& xpr) + : m_result(xpr.rows(), xpr.cols()) + { + ::new (static_cast(this)) Base(m_result); + generic_product_impl::evalTo(m_result, xpr.lhs(), xpr.rhs()); + } + +protected: + PlainObject m_result; +}; + +template +struct product_evaluator, DefaultProduct>, ProductTag, DenseShape, DenseShape, typename traits::Scalar, typename traits::Scalar> + : public evaluator, DefaultProduct>::PlainObject>::type +{ + typedef Homogeneous Rhs; + typedef Product XprType; + typedef typename XprType::PlainObject PlainObject; + typedef typename evaluator::type Base; + + product_evaluator(const XprType& xpr) + : m_result(xpr.rows(), xpr.cols()) + { + ::new (static_cast(this)) Base(m_result); + generic_product_impl::evalTo(m_result, xpr.lhs(), xpr.rhs()); + } + +protected: + PlainObject m_result; +}; + +template +struct product_evaluator, Homogeneous, DefaultProduct>, ProductTag, DenseShape, DenseShape, Scalar, typename traits::Scalar> + : public evaluator, Homogeneous, DefaultProduct>::PlainObject>::type +{ + typedef Transform Lhs; + typedef Homogeneous Rhs; + typedef Product XprType; + typedef typename XprType::PlainObject PlainObject; + typedef typename evaluator::type Base; + + product_evaluator(const XprType& xpr) + : m_result(xpr.rows(), xpr.cols()) + { + ::new (static_cast(this)) Base(m_result); + generic_product_impl::evalTo(m_result, xpr.lhs(), xpr.rhs()); + } + +protected: + PlainObject m_result; +}; + +#endif // EIGEN_TEST_EVALUATORS + } // end namespace internal } // end namespace Eigen diff --git a/Eigen/src/Geometry/Transform.h b/Eigen/src/Geometry/Transform.h index cb93acf6b..54d05f9cf 100644 --- a/Eigen/src/Geometry/Transform.h +++ b/Eigen/src/Geometry/Transform.h @@ -62,6 +62,23 @@ struct transform_construct_from_matrix; template struct transform_take_affine_part; +#ifdef EIGEN_TEST_EVALUATORS +template +struct traits > +{ + typedef _Scalar Scalar; + typedef DenseIndex Index; + typedef Dense StorageKind; + enum { + RowsAtCompileTime = _Dim, + ColsAtCompileTime = _Dim, + MaxRowsAtCompileTime = _Dim, + MaxColsAtCompileTime = _Dim, + Flags = 0 + }; +}; +#endif + } // end namespace internal /** \geometry_module \ingroup Geometry_Module @@ -355,6 +372,11 @@ public: inline Transform& operator=(const QTransform& other); inline QTransform toQTransform(void) const; #endif + +#ifdef EIGEN_TEST_EVALUATORS + Index rows() const { return m_matrix.cols(); } + Index cols() const { return m_matrix.cols(); } +#endif /** shortcut for m_matrix(row,col); * \sa MatrixBase::operator(Index,Index) const */ -- cgit v1.2.3