allow to multiply a householder sequence and a matrix when one is real and one is complex.

This is especially important as in bidiagonalization, the band matrix is real.
This commit is contained in:
Benoit Jacob 2010-01-15 00:35:26 -05:00
parent ddc32adb0e
commit bfe6fdde24
2 changed files with 24 additions and 8 deletions

View File

@ -88,13 +88,28 @@ struct ei_hseq_side_dependent_impl<VectorsType, CoeffsType, OnTheRight>
} }
}; };
template<typename OtherScalarType, typename MatrixType> struct ei_matrix_type_times_scalar_type
{
typedef typename ei_scalar_product_traits<OtherScalarType, typename MatrixType::Scalar>::ReturnType
ResultScalar;
typedef Matrix<ResultScalar, MatrixType::RowsAtCompileTime, MatrixType::ColsAtCompileTime,
0, MatrixType::MaxRowsAtCompileTime, MatrixType::MaxColsAtCompileTime> Type;
};
template<typename VectorsType, typename CoeffsType, int Side> class HouseholderSequence template<typename VectorsType, typename CoeffsType, int Side> class HouseholderSequence
: public AnyMatrixBase<HouseholderSequence<VectorsType,CoeffsType,Side> > : public AnyMatrixBase<HouseholderSequence<VectorsType,CoeffsType,Side> >
{ {
typedef typename VectorsType::Scalar Scalar; enum {
RowsAtCompileTime = ei_traits<HouseholderSequence>::RowsAtCompileTime,
ColsAtCompileTime = ei_traits<HouseholderSequence>::ColsAtCompileTime,
MaxRowsAtCompileTime = ei_traits<HouseholderSequence>::MaxRowsAtCompileTime,
MaxColsAtCompileTime = ei_traits<HouseholderSequence>::MaxColsAtCompileTime
};
typedef typename ei_traits<HouseholderSequence>::Scalar Scalar;
typedef typename ei_hseq_side_dependent_impl<VectorsType,CoeffsType,Side>::EssentialVectorType typedef typename ei_hseq_side_dependent_impl<VectorsType,CoeffsType,Side>::EssentialVectorType
EssentialVectorType; EssentialVectorType;
public: public:
typedef HouseholderSequence< typedef HouseholderSequence<
@ -179,17 +194,19 @@ template<typename VectorsType, typename CoeffsType, int Side> class HouseholderS
} }
template<typename OtherDerived> template<typename OtherDerived>
typename OtherDerived::PlainMatrixType operator*(const MatrixBase<OtherDerived>& other) const typename ei_matrix_type_times_scalar_type<Scalar, OtherDerived>::Type operator*(const MatrixBase<OtherDerived>& other) const
{ {
typename OtherDerived::PlainMatrixType res(other); typename ei_matrix_type_times_scalar_type<Scalar, OtherDerived>::Type
res(other.template cast<typename ei_matrix_type_times_scalar_type<Scalar, OtherDerived>::ResultScalar>());
applyThisOnTheLeft(res); applyThisOnTheLeft(res);
return res; return res;
} }
template<typename OtherDerived> friend template<typename OtherDerived> friend
typename OtherDerived::PlainMatrixType operator*(const MatrixBase<OtherDerived>& other, const HouseholderSequence& h) typename ei_matrix_type_times_scalar_type<Scalar, OtherDerived>::Type operator*(const MatrixBase<OtherDerived>& other, const HouseholderSequence& h)
{ {
typename OtherDerived::PlainMatrixType res(other); typename ei_matrix_type_times_scalar_type<Scalar, OtherDerived>::Type
res(other.template cast<typename ei_matrix_type_times_scalar_type<Scalar, OtherDerived>::ResultScalar>());
h.applyThisOnTheRight(res); h.applyThisOnTheRight(res);
return res; return res;
} }

View File

@ -24,7 +24,6 @@
#include "main.h" #include "main.h"
#include <Eigen/SVD> #include <Eigen/SVD>
#include <Eigen/LU>
template<typename MatrixType> void upperbidiag(const MatrixType& m) template<typename MatrixType> void upperbidiag(const MatrixType& m)
{ {
@ -39,7 +38,7 @@ template<typename MatrixType> void upperbidiag(const MatrixType& m)
RealMatrixType b(rows, cols); RealMatrixType b(rows, cols);
b.setZero(); b.setZero();
b.block(0,0,cols,cols) = ubd.bidiagonal(); b.block(0,0,cols,cols) = ubd.bidiagonal();
MatrixType c = ubd.householderU() * b.template cast<Scalar>() * ubd.householderV().adjoint(); MatrixType c = ubd.householderU() * b * ubd.householderV().adjoint();
VERIFY_IS_APPROX(a,c); VERIFY_IS_APPROX(a,c);
} }