diff options
author | 2015-04-18 22:43:27 +0200 | |
---|---|---|
committer | 2015-04-18 22:43:27 +0200 | |
commit | 5a3c48e3c6c6a3966b68f715610e0eaafa906b2a (patch) | |
tree | 24881445e1f4918309957ffadc25af7258599971 | |
parent | 3b429b71e65916b689d0d16e0fac358a79f2dfbe (diff) |
bug #942: fix dangling references in evaluator of diagonal * sparse products.
-rw-r--r-- | Eigen/src/SparseCore/SparseDiagonalProduct.h | 6 | ||||
-rw-r--r-- | test/sparse_product.cpp | 24 |
2 files changed, 29 insertions, 1 deletions
diff --git a/Eigen/src/SparseCore/SparseDiagonalProduct.h b/Eigen/src/SparseCore/SparseDiagonalProduct.h index b7598c885..fdc4bd495 100644 --- a/Eigen/src/SparseCore/SparseDiagonalProduct.h +++ b/Eigen/src/SparseCore/SparseDiagonalProduct.h @@ -107,7 +107,9 @@ struct sparse_diagonal_product_evaluator<SparseXprType, DiagCoeffType, SDP_AsCwi { public: InnerIterator(const sparse_diagonal_product_evaluator &xprEval, Index outer) - : m_cwiseEval(xprEval.m_sparseXprNested.innerVector(outer).cwiseProduct(xprEval.m_diagCoeffNested)), + : m_innerVectorXpr(xprEval.m_sparseXprNested.innerVector(outer)), + m_cwiseXpr(m_innerVectorXpr.cwiseProduct(xprEval.m_diagCoeffNested)), + m_cwiseEval(m_cwiseXpr), m_cwiseIter(m_cwiseEval, 0), m_outer(outer) {} @@ -123,6 +125,8 @@ struct sparse_diagonal_product_evaluator<SparseXprType, DiagCoeffType, SDP_AsCwi inline operator bool() const { return m_cwiseIter; } protected: + const typename SparseXprType::ConstInnerVectorReturnType m_innerVectorXpr; + const CwiseProductType m_cwiseXpr; CwiseProductEval m_cwiseEval; CwiseProductIterator m_cwiseIter; Index m_outer; diff --git a/test/sparse_product.cpp b/test/sparse_product.cpp index 3bad3def7..201d5bc49 100644 --- a/test/sparse_product.cpp +++ b/test/sparse_product.cpp @@ -278,11 +278,35 @@ template<typename SparseMatrixType, typename DenseMatrixType> void sparse_produc VERIFY_IS_APPROX( m4(0,0), 0.0 ); } +template<typename Scalar> +void bug_942() +{ + typedef Matrix<Scalar, Dynamic, 1> Vector; + typedef SparseMatrix<Scalar, ColMajor> ColSpMat; + typedef SparseMatrix<Scalar, RowMajor> RowSpMat; + ColSpMat cmA(1,1); + cmA.insert(0,0) = 1; + + RowSpMat rmA(1,1); + rmA.insert(0,0) = 1; + + Vector d(1); + d[0] = 2; + + double res = 2; + + VERIFY_IS_APPROX( ( cmA*d.asDiagonal() ).eval().coeff(0,0), res ); + VERIFY_IS_APPROX( ( d.asDiagonal()*rmA ).eval().coeff(0,0), res ); + VERIFY_IS_APPROX( ( rmA*d.asDiagonal() ).eval().coeff(0,0), res ); + VERIFY_IS_APPROX( ( d.asDiagonal()*cmA ).eval().coeff(0,0), res ); +} + void test_sparse_product() { for(int i = 0; i < g_repeat; i++) { CALL_SUBTEST_1( (sparse_product<SparseMatrix<double,ColMajor> >()) ); CALL_SUBTEST_1( (sparse_product<SparseMatrix<double,RowMajor> >()) ); + CALL_SUBTEST_1( (bug_942<double>()) ); CALL_SUBTEST_2( (sparse_product<SparseMatrix<std::complex<double>, ColMajor > >()) ); CALL_SUBTEST_2( (sparse_product<SparseMatrix<std::complex<double>, RowMajor > >()) ); CALL_SUBTEST_3( (sparse_product<SparseMatrix<float,ColMajor,long int> >()) ); |