diff options
-rw-r--r-- | Eigen/src/Core/functors/UnaryFunctors.h | 10 | ||||
-rw-r--r-- | test/product_notemporary.cpp | 2 |
2 files changed, 11 insertions, 1 deletions
diff --git a/Eigen/src/Core/functors/UnaryFunctors.h b/Eigen/src/Core/functors/UnaryFunctors.h index 55994047e..1d5eb3678 100644 --- a/Eigen/src/Core/functors/UnaryFunctors.h +++ b/Eigen/src/Core/functors/UnaryFunctors.h @@ -117,7 +117,15 @@ template<typename Scalar> struct functor_traits<scalar_conjugate_op<Scalar> > { enum { - Cost = NumTraits<Scalar>::IsComplex ? NumTraits<Scalar>::AddCost : 0, + Cost = 0, + // Yes the cost is zero even for complexes because in most cases for which + // the cost is used, conjugation turns to be a no-op. Some examples: + // cost(a*conj(b)) == cost(a*b) + // cost(a+conj(b)) == cost(a+b) + // <etc. + // If we don't set it to zero, then: + // A.conjugate().lazyProduct(B.conjugate()) + // will bake its operands. We definitely don't want that! PacketAccess = packet_traits<Scalar>::HasConj }; }; diff --git a/test/product_notemporary.cpp b/test/product_notemporary.cpp index 7f169e6ae..8b6419d0c 100644 --- a/test/product_notemporary.cpp +++ b/test/product_notemporary.cpp @@ -134,7 +134,9 @@ template<typename MatrixType> void product_notemporary(const MatrixType& m) VERIFY_EVALUATION_COUNT( m3.noalias() = m1.block(r0,r0,r1,r1).template triangularView<UnitUpper>() * m2.block(r0,c0,r1,c1), 1); // Zero temporaries for lazy products ... + m3.setRandom(rows,cols); VERIFY_EVALUATION_COUNT( Scalar tmp = 0; tmp += Scalar(RealScalar(1)) / (m3.transpose().lazyProduct(m3)).diagonal().sum(), 0 ); + VERIFY_EVALUATION_COUNT( m3.noalias() = m1.conjugate().lazyProduct(m2.conjugate()), 0); // ... and even no temporary for even deeply (>=2) nested products VERIFY_EVALUATION_COUNT( Scalar tmp = 0; tmp += Scalar(RealScalar(1)) / (m3.transpose() * m3).diagonal().sum(), 0 ); |