mirror of
https://gitlab.com/libeigen/eigen.git
synced 2025-07-31 17:22:07 +08:00
Add row/column-wise reverseInPlace feature.
This commit is contained in:
parent
dfb674a25e
commit
8313fb7df7
@ -200,13 +200,13 @@ DenseBase<Derived>::reverse() const
|
|||||||
* In most cases it is probably better to simply use the reversed expression
|
* In most cases it is probably better to simply use the reversed expression
|
||||||
* of a matrix. However, when reversing the matrix data itself is really needed,
|
* of a matrix. However, when reversing the matrix data itself is really needed,
|
||||||
* then this "in-place" version is probably the right choice because it provides
|
* then this "in-place" version is probably the right choice because it provides
|
||||||
* the following additional features:
|
* the following additional benefits:
|
||||||
* - less error prone: doing the same operation with .reverse() requires special care:
|
* - less error prone: doing the same operation with .reverse() requires special care:
|
||||||
* \code m = m.reverse().eval(); \endcode
|
* \code m = m.reverse().eval(); \endcode
|
||||||
* - this API allows to avoid creating a temporary (the current implementation creates a temporary, but that could be avoided using swap)
|
* - this API enables reverse operations without the need for a temporary
|
||||||
* - it allows future optimizations (cache friendliness, etc.)
|
* - it allows future optimizations (cache friendliness, etc.)
|
||||||
*
|
*
|
||||||
* \sa reverse() */
|
* \sa VectorwiseOp::reverseInPlace(), reverse() */
|
||||||
template<typename Derived>
|
template<typename Derived>
|
||||||
inline void DenseBase<Derived>::reverseInPlace()
|
inline void DenseBase<Derived>::reverseInPlace()
|
||||||
{
|
{
|
||||||
@ -232,6 +232,52 @@ inline void DenseBase<Derived>::reverseInPlace()
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
namespace internal {
|
||||||
|
|
||||||
|
template<int Direction>
|
||||||
|
struct vectorwise_reverse_inplace_impl;
|
||||||
|
|
||||||
|
template<>
|
||||||
|
struct vectorwise_reverse_inplace_impl<Vertical>
|
||||||
|
{
|
||||||
|
template<typename ExpressionType>
|
||||||
|
static void run(ExpressionType &xpr)
|
||||||
|
{
|
||||||
|
Index half = xpr.rows()/2;
|
||||||
|
xpr.topRows(half).swap(xpr.bottomRows(half).colwise().reverse());
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
template<>
|
||||||
|
struct vectorwise_reverse_inplace_impl<Horizontal>
|
||||||
|
{
|
||||||
|
template<typename ExpressionType>
|
||||||
|
static void run(ExpressionType &xpr)
|
||||||
|
{
|
||||||
|
Index half = xpr.cols()/2;
|
||||||
|
xpr.leftCols(half).swap(xpr.rightCols(half).rowwise().reverse());
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
} // end namespace internal
|
||||||
|
|
||||||
|
/** This is the "in place" version of VectorwiseOp::reverse: it reverses each column or row of \c *this.
|
||||||
|
*
|
||||||
|
* In most cases it is probably better to simply use the reversed expression
|
||||||
|
* of a matrix. However, when reversing the matrix data itself is really needed,
|
||||||
|
* then this "in-place" version is probably the right choice because it provides
|
||||||
|
* the following additional benefits:
|
||||||
|
* - less error prone: doing the same operation with .reverse() requires special care:
|
||||||
|
* \code m = m.reverse().eval(); \endcode
|
||||||
|
* - this API enables reverse operations without the need for a temporary
|
||||||
|
*
|
||||||
|
* \sa DenseBase::reverseInPlace(), reverse() */
|
||||||
|
template<typename ExpressionType, int Direction>
|
||||||
|
void VectorwiseOp<ExpressionType,Direction>::reverseInPlace()
|
||||||
|
{
|
||||||
|
internal::vectorwise_reverse_inplace_impl<Direction>::run(_expression().const_cast_derived());
|
||||||
|
}
|
||||||
|
|
||||||
} // end namespace Eigen
|
} // end namespace Eigen
|
||||||
|
|
||||||
#endif // EIGEN_REVERSE_H
|
#endif // EIGEN_REVERSE_H
|
||||||
|
@ -563,6 +563,8 @@ template<typename ExpressionType, int Direction> class VectorwiseOp
|
|||||||
m_matrix = this->normalized();
|
m_matrix = this->normalized();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
inline void reverseInPlace();
|
||||||
|
|
||||||
/////////// Geometry module ///////////
|
/////////// Geometry module ///////////
|
||||||
|
|
||||||
typedef Homogeneous<ExpressionType,Direction> HomogeneousReturnType;
|
typedef Homogeneous<ExpressionType,Direction> HomogeneousReturnType;
|
||||||
|
@ -109,6 +109,14 @@ template<typename MatrixType> void reverse(const MatrixType& m)
|
|||||||
m2.row(0).reverseInPlace();
|
m2.row(0).reverseInPlace();
|
||||||
VERIFY_IS_APPROX(m2.row(0),m1.row(0).reverse().eval());
|
VERIFY_IS_APPROX(m2.row(0),m1.row(0).reverse().eval());
|
||||||
|
|
||||||
|
m2 = m1;
|
||||||
|
m2.rowwise().reverseInPlace();
|
||||||
|
VERIFY_IS_APPROX(m2,m1.rowwise().reverse().eval());
|
||||||
|
|
||||||
|
m2 = m1;
|
||||||
|
m2.colwise().reverseInPlace();
|
||||||
|
VERIFY_IS_APPROX(m2,m1.colwise().reverse().eval());
|
||||||
|
|
||||||
/*
|
/*
|
||||||
m1.colwise().reverse()(r, c) = x;
|
m1.colwise().reverse()(r, c) = x;
|
||||||
VERIFY_IS_APPROX(x, m1(rows - 1 - r, c));
|
VERIFY_IS_APPROX(x, m1(rows - 1 - r, c));
|
||||||
|
Loading…
x
Reference in New Issue
Block a user