35 #ifndef _BLAZE_MATH_EXPRESSIONS_TDMATSMATMULTEXPR_H_
36 #define _BLAZE_MATH_EXPRESSIONS_TDMATSMATMULTEXPR_H_
119 template<
typename MT1
121 class TDMatSMatMultExpr :
public DenseMatrix< TDMatSMatMultExpr<MT1,MT2>, true >
122 ,
private MatMatMultExpr
123 ,
private Computation
154 template<
typename T1,
typename T2,
typename T3 >
155 struct CanExploitSymmetry {
156 enum { value = ( IsRowMajorMatrix<T1>::value && IsSymmetric<T2>::value ) ||
157 ( IsColumnMajorMatrix<T1>::value && IsSymmetric<T3>::value ) };
168 template<
typename T1,
typename T2,
typename T3 >
169 struct IsEvaluationRequired {
170 enum { value = ( evaluateLeft || evaluateRight ) &&
171 !CanExploitSymmetry<T1,T2,T3>::value };
182 template<
typename T1,
typename T2,
typename T3 >
183 struct UseOptimizedKernel {
184 enum { value = !IsDiagonal<T2>::value &&
185 !IsResizable<typename T1::ElementType>::value &&
186 !( IsColumnMajorMatrix<T1>::value && IsResizable<ET2>::value ) };
196 template<
typename T1,
typename T2,
typename T3 >
197 struct UseDefaultKernel {
198 enum { value = !UseOptimizedKernel<T1,T2,T3>::value };
228 enum { vectorizable = 0 };
231 enum { smpAssignable = !evaluateLeft && MT1::smpAssignable &&
232 !evaluateRight && MT2::smpAssignable };
275 :(
lhs_.columns() ) ) );
277 if(
lhs_.columns() == 0UL ||
281 ElementType tmp(
lhs_(i,kbegin) *
rhs_(kbegin,j) );
282 for(
size_t k=kbegin+1UL; k<kend; ++k ) {
306 return rhs_.columns();
336 template<
typename T >
338 return (
lhs_.isAliased( alias ) ||
rhs_.isAliased( alias ) );
348 template<
typename T >
350 return (
lhs_.isAliased( alias ) ||
rhs_.isAliased( alias ) );
360 return lhs_.isAligned();
393 template<
typename MT >
404 LT A(
serial( rhs.lhs_ ) );
405 RT B(
serial( rhs.rhs_ ) );
414 TDMatSMatMultExpr::selectRowMajorAssignKernel( ~lhs, A, B );
434 template<
typename MT3
438 selectRowMajorAssignKernel( MT3& C,
const MT4& A,
const MT5& B )
442 for(
size_t i=0UL; i<A.rows(); ++i )
444 for(
size_t j=0UL; j<C.columns(); ++j ) {
448 if( IsDiagonal<MT4>::value )
450 ConstIterator element( B.begin(i) );
451 const ConstIterator
end( B.end(i) );
453 for( ; element!=
end; ++element ) {
454 C(i,element->index()) = A(i,i) * element->value();
459 const size_t jbegin( ( IsUpper<MT4>::value )
460 ?( IsStrictlyUpper<MT4>::value ? i+1UL : i )
462 const size_t jend( ( IsLower<MT4>::value )
463 ?( IsStrictlyLower<MT4>::value ? i : i+1UL )
467 for(
size_t j=jbegin; j<jend; ++j )
469 ConstIterator element( B.begin(j) );
470 const ConstIterator
end( B.end(j) );
472 for( ; element!=
end; ++element ) {
474 C(i,element->index()) = A(i,j) * element->value();
476 C(i,element->index()) += A(i,j) * element->value();
500 template<
typename MT3
503 static inline typename EnableIf< UseOptimizedKernel<MT3,MT4,MT5> >::Type
504 selectRowMajorAssignKernel( MT3& C,
const MT4& A,
const MT5& B )
508 const size_t ipos( A.rows() & size_t(-4) );
511 for(
size_t i=0UL; i<ipos; i+=4 )
513 for(
size_t j=0UL; j<C.columns(); ++j ) {
520 const size_t jbegin( ( IsUpper<MT4>::value )
521 ?( IsStrictlyUpper<MT4>::value ? i+1UL : i )
523 const size_t jend( ( IsLower<MT4>::value )
524 ?( IsStrictlyLower<MT4>::value ? i+3UL : i+4UL )
528 for(
size_t j=jbegin; j<jend; ++j )
530 ConstIterator element( B.begin(j) );
531 const ConstIterator
end( B.end(j) );
533 for( ; element!=
end; ++element ) {
534 C(i ,element->index()) += A(i ,j) * element->value();
535 C(i+1UL,element->index()) += A(i+1UL,j) * element->value();
536 C(i+2UL,element->index()) += A(i+2UL,j) * element->value();
537 C(i+3UL,element->index()) += A(i+3UL,j) * element->value();
542 for(
size_t i=ipos; i<A.rows(); ++i )
544 for(
size_t j=0UL; j<C.columns(); ++j ) {
548 const size_t jbegin( ( IsUpper<MT4>::value )
549 ?( IsStrictlyUpper<MT4>::value ? i+1UL : i )
551 const size_t jend( ( IsLower<MT4>::value )
552 ?( IsStrictlyLower<MT4>::value ? i : i+1UL )
556 for(
size_t j=jbegin; j<jend; ++j )
558 ConstIterator element( B.begin(j) );
559 const ConstIterator
end( B.end(j) );
561 for( ; element!=
end; ++element ) {
562 C(i,element->index()) += A(i,j) * element->value();
583 template<
typename MT >
584 friend inline typename DisableIf< CanExploitSymmetry<MT,MT1,MT2> >::Type
592 LT A(
serial( rhs.lhs_ ) );
593 RT B(
serial( rhs.rhs_ ) );
602 TDMatSMatMultExpr::selectColumnMajorAssignKernel( ~lhs, A, B );
622 template<
typename MT3
625 static inline typename EnableIf< UseDefaultKernel<MT3,MT4,MT5> >::Type
626 selectColumnMajorAssignKernel( MT3& C,
const MT4& A,
const MT5& B )
632 for(
size_t j=0UL; j<B.rows(); ++j )
634 ConstIterator element( B.begin(j) );
635 const ConstIterator
end( B.end(j) );
637 if( IsDiagonal<MT4>::value )
639 for( ; element!=
end; ++element ) {
640 C(j,element->index()) = A(j,j) * element->value();
645 const size_t ibegin( ( IsLower<MT4>::value )
646 ?( IsStrictlyLower<MT4>::value ? j+1UL : j )
648 const size_t iend( ( IsUpper<MT4>::value )
649 ?( IsStrictlyUpper<MT4>::value ? j : j+1UL )
653 for( ; element!=
end; ++element ) {
654 for(
size_t i=ibegin; i<iend; ++i ) {
656 C(i,element->index()) = A(i,j) * element->value();
658 C(i,element->index()) += A(i,j) * element->value();
682 template<
typename MT3
685 static inline typename EnableIf< UseOptimizedKernel<MT3,MT4,MT5> >::Type
686 selectColumnMajorAssignKernel( MT3& C,
const MT4& A,
const MT5& B )
694 for(
size_t j=0UL; j<B.rows(); ++j )
696 ConstIterator element( B.begin(j) );
697 const ConstIterator
end( B.end(j) );
699 const size_t nonzeros( B.nonZeros(j) );
700 const size_t kpos( nonzeros &
size_t(-4) );
703 const size_t ibegin( ( IsLower<MT4>::value )
704 ?( IsStrictlyLower<MT4>::value ? j+1UL : j )
706 const size_t iend( ( IsUpper<MT4>::value )
707 ?( IsStrictlyUpper<MT4>::value ? j : j+1UL )
711 const size_t inum( iend - ibegin );
712 const size_t ipos( ibegin + ( inum &
size_t(-4) ) );
715 for(
size_t k=0UL; k<kpos; k+=4UL )
717 const size_t j1( element->index() );
718 const ET2 v1( element->value() );
720 const size_t j2( element->index() );
721 const ET2 v2( element->value() );
723 const size_t j3( element->index() );
724 const ET2 v3( element->value() );
726 const size_t j4( element->index() );
727 const ET2 v4( element->value() );
732 for( i=ibegin; i<ipos; i+=4UL ) {
733 C(i ,j1) += A(i ,j) * v1;
734 C(i+1UL,j1) += A(i+1UL,j) * v1;
735 C(i+2UL,j1) += A(i+2UL,j) * v1;
736 C(i+3UL,j1) += A(i+3UL,j) * v1;
737 C(i ,j2) += A(i ,j) * v2;
738 C(i+1UL,j2) += A(i+1UL,j) * v2;
739 C(i+2UL,j2) += A(i+2UL,j) * v2;
740 C(i+3UL,j2) += A(i+3UL,j) * v2;
741 C(i ,j3) += A(i ,j) * v3;
742 C(i+1UL,j3) += A(i+1UL,j) * v3;
743 C(i+2UL,j3) += A(i+2UL,j) * v3;
744 C(i+3UL,j3) += A(i+3UL,j) * v3;
745 C(i ,j4) += A(i ,j) * v4;
746 C(i+1UL,j4) += A(i+1UL,j) * v4;
747 C(i+2UL,j4) += A(i+2UL,j) * v4;
748 C(i+3UL,j4) += A(i+3UL,j) * v4;
750 for( ; i<iend; ++i ) {
751 C(i,j1) += A(i,j) * v1;
752 C(i,j2) += A(i,j) * v2;
753 C(i,j3) += A(i,j) * v3;
754 C(i,j4) += A(i,j) * v4;
758 for( ; element!=
end; ++element )
760 const size_t j1( element->index() );
761 const ET2 v1( element->value() );
763 for( i=ibegin; i<ipos; i+=4UL ) {
764 C(i ,j1) += A(i ,j) * v1;
765 C(i+1UL,j1) += A(i+1UL,j) * v1;
766 C(i+2UL,j1) += A(i+2UL,j) * v1;
767 C(i+3UL,j1) += A(i+3UL,j) * v1;
769 for( ; i<iend; ++i ) {
770 C(i,j1) += A(i,j) * v1;
791 template<
typename MT
793 friend inline typename DisableIf< CanExploitSymmetry<MT,MT1,MT2> >::Type
798 typedef typename SelectType< SO, ResultType, OppositeType >::Type TmpType;
810 const TmpType tmp(
serial( rhs ) );
831 template<
typename MT >
832 friend inline typename EnableIf< CanExploitSymmetry<MT,MT1,MT2> >::Type
862 template<
typename MT >
863 friend inline typename EnableIf< CanExploitSymmetry<MT,MT1,MT2> >::Type
889 template<
typename MT >
890 friend inline typename DisableIf< CanExploitSymmetry<MT,MT1,MT2> >::Type
900 LT A(
serial( rhs.lhs_ ) );
901 RT B(
serial( rhs.rhs_ ) );
910 TDMatSMatMultExpr::selectRowMajorAddAssignKernel( ~lhs, A, B );
929 template<
typename MT3
932 static inline void selectRowMajorAddAssignKernel( MT3& C,
const MT4& A,
const MT5& B )
938 if( !IsDiagonal<MT4>::value )
940 const size_t ipos( A.rows() & size_t(-4) );
943 for( ; i<ipos; i+=4UL )
945 const size_t jbegin( ( IsUpper<MT4>::value )
946 ?( IsStrictlyUpper<MT4>::value ? i+1UL : i )
948 const size_t jend( ( IsLower<MT4>::value )
949 ?( IsStrictlyLower<MT4>::value ? i+3UL : i+4UL )
953 for(
size_t j=jbegin; j<jend; ++j )
955 ConstIterator element( B.begin(j) );
956 const ConstIterator
end( B.end(j) );
958 for( ; element!=
end; ++element ) {
959 C(i ,element->index()) += A(i ,j) * element->value();
960 C(i+1UL,element->index()) += A(i+1UL,j) * element->value();
961 C(i+2UL,element->index()) += A(i+2UL,j) * element->value();
962 C(i+3UL,element->index()) += A(i+3UL,j) * element->value();
968 for( ; i<A.rows(); ++i )
970 if( IsDiagonal<MT4>::value )
972 ConstIterator element( B.begin(i) );
973 const ConstIterator
end( B.end(i) );
975 for( ; element!=
end; ++element ) {
976 C(i,element->index()) += A(i,i) * element->value();
981 const size_t jbegin( ( IsUpper<MT4>::value )
982 ?( IsStrictlyUpper<MT4>::value ? i+1UL : i )
984 const size_t jend( ( IsLower<MT4>::value )
985 ?( IsStrictlyLower<MT4>::value ? i : i+1UL )
989 for(
size_t j=jbegin; j<jend; ++j )
991 ConstIterator element( B.begin(j) );
992 const ConstIterator
end( B.end(j) );
994 for( ; element!=
end; ++element ) {
995 C(i,element->index()) += A(i,j) * element->value();
1017 template<
typename MT >
1018 friend inline typename DisableIf< CanExploitSymmetry<MT,MT1,MT2> >::Type
1026 LT A(
serial( rhs.lhs_ ) );
1027 RT B(
serial( rhs.rhs_ ) );
1036 TDMatSMatMultExpr::selectColumnMajorAddAssignKernel( ~lhs, A, B );
1055 template<
typename MT3
1058 static inline typename EnableIf< UseDefaultKernel<MT3,MT4,MT5> >::Type
1059 selectColumnMajorAddAssignKernel( MT3& C,
const MT4& A,
const MT5& B )
1065 for(
size_t j=0UL; j<B.rows(); ++j )
1067 ConstIterator element( B.begin(j) );
1068 const ConstIterator
end( B.end(j) );
1070 if( IsDiagonal<MT4>::value )
1072 for( ; element!=
end; ++element ) {
1073 C(j,element->index()) += A(j,j) * element->value();
1078 const size_t ibegin( ( IsLower<MT4>::value )
1079 ?( IsStrictlyLower<MT4>::value ? j+1UL : j )
1081 const size_t iend( ( IsUpper<MT4>::value )
1082 ?( IsStrictlyUpper<MT4>::value ? j : j+1UL )
1086 const size_t inum( iend - ibegin );
1087 const size_t ipos( ibegin + ( inum &
size_t(-4) ) );
1090 for( ; element!=
end; ++element ) {
1091 for( i=ibegin; i<ipos; i+=4UL ) {
1092 C(i ,element->index()) += A(i ,j) * element->value();
1093 C(i+1UL,element->index()) += A(i+1UL,j) * element->value();
1094 C(i+2UL,element->index()) += A(i+2UL,j) * element->value();
1095 C(i+3UL,element->index()) += A(i+3UL,j) * element->value();
1097 for( ; i<iend; ++i ) {
1098 C(i,element->index()) += A(i,j) * element->value();
1121 template<
typename MT3
1124 static inline typename EnableIf< UseOptimizedKernel<MT3,MT4,MT5> >::Type
1125 selectColumnMajorAddAssignKernel( MT3& C,
const MT4& A,
const MT5& B )
1131 for(
size_t j=0UL; j<B.rows(); ++j )
1133 ConstIterator element( B.begin(j) );
1134 const ConstIterator
end( B.end(j) );
1136 const size_t nonzeros( B.nonZeros(j) );
1137 const size_t kpos( nonzeros &
size_t(-4) );
1140 const size_t ibegin( ( IsLower<MT4>::value )
1141 ?( IsStrictlyLower<MT4>::value ? j+1UL : j )
1143 const size_t iend( ( IsUpper<MT4>::value )
1144 ?( IsStrictlyUpper<MT4>::value ? j : j+1UL )
1148 const size_t inum( iend - ibegin );
1149 const size_t ipos( ibegin + ( inum &
size_t(-4) ) );
1152 for(
size_t k=0UL; k<kpos; k+=4UL )
1154 const size_t j1( element->index() );
1155 const ET2 v1( element->value() );
1157 const size_t j2( element->index() );
1158 const ET2 v2( element->value() );
1160 const size_t j3( element->index() );
1161 const ET2 v3( element->value() );
1163 const size_t j4( element->index() );
1164 const ET2 v4( element->value() );
1169 for( i=ibegin; i<ipos; i+=4UL ) {
1170 C(i ,j1) += A(i ,j) * v1;
1171 C(i+1UL,j1) += A(i+1UL,j) * v1;
1172 C(i+2UL,j1) += A(i+2UL,j) * v1;
1173 C(i+3UL,j1) += A(i+3UL,j) * v1;
1174 C(i ,j2) += A(i ,j) * v2;
1175 C(i+1UL,j2) += A(i+1UL,j) * v2;
1176 C(i+2UL,j2) += A(i+2UL,j) * v2;
1177 C(i+3UL,j2) += A(i+3UL,j) * v2;
1178 C(i ,j3) += A(i ,j) * v3;
1179 C(i+1UL,j3) += A(i+1UL,j) * v3;
1180 C(i+2UL,j3) += A(i+2UL,j) * v3;
1181 C(i+3UL,j3) += A(i+3UL,j) * v3;
1182 C(i ,j4) += A(i ,j) * v4;
1183 C(i+1UL,j4) += A(i+1UL,j) * v4;
1184 C(i+2UL,j4) += A(i+2UL,j) * v4;
1185 C(i+3UL,j4) += A(i+3UL,j) * v4;
1187 for( ; i<iend; ++i ) {
1188 C(i,j1) += A(i,j) * v1;
1189 C(i,j2) += A(i,j) * v2;
1190 C(i,j3) += A(i,j) * v3;
1191 C(i,j4) += A(i,j) * v4;
1195 for( ; element!=
end; ++element )
1197 const size_t j1( element->index() );
1198 const ET2 v1( element->value() );
1200 for( i=ibegin; i<ipos; i+=4UL ) {
1201 C(i ,j1) += A(i ,j) * v1;
1202 C(i+1UL,j1) += A(i+1UL,j) * v1;
1203 C(i+2UL,j1) += A(i+2UL,j) * v1;
1204 C(i+3UL,j1) += A(i+3UL,j) * v1;
1206 for( ; i<iend; ++i ) {
1207 C(i,j1) += A(i,j) * v1;
1231 template<
typename MT >
1232 friend inline typename EnableIf< CanExploitSymmetry<MT,MT1,MT2> >::Type
1262 template<
typename MT >
1263 friend inline typename EnableIf< CanExploitSymmetry<MT,MT1,MT2> >::Type
1293 template<
typename MT >
1294 friend inline typename DisableIf< CanExploitSymmetry<MT,MT1,MT2> >::Type
1304 LT A(
serial( rhs.lhs_ ) );
1305 RT B(
serial( rhs.rhs_ ) );
1314 TDMatSMatMultExpr::selectRowMajorSubAssignKernel( ~lhs, A, B );
1333 template<
typename MT3
1336 static inline void selectRowMajorSubAssignKernel( MT3& C,
const MT4& A,
const MT5& B )
1342 if( !IsDiagonal<MT4>::value )
1344 const size_t ipos( A.rows() & size_t(-4) );
1347 for( ; i<ipos; i+=4UL )
1349 const size_t jbegin( ( IsUpper<MT4>::value )
1350 ?( IsStrictlyUpper<MT4>::value ? i+1UL : i )
1352 const size_t jend( ( IsLower<MT4>::value )
1353 ?( IsStrictlyLower<MT4>::value ? i+3UL : i+4UL )
1357 for(
size_t j=jbegin; j<jend; ++j )
1359 ConstIterator element( B.begin(j) );
1360 const ConstIterator
end( B.end(j) );
1362 for( ; element!=
end; ++element ) {
1363 C(i ,element->index()) -= A(i ,j) * element->value();
1364 C(i+1UL,element->index()) -= A(i+1UL,j) * element->value();
1365 C(i+2UL,element->index()) -= A(i+2UL,j) * element->value();
1366 C(i+3UL,element->index()) -= A(i+3UL,j) * element->value();
1372 for( ; i<A.rows(); ++i )
1374 if( IsDiagonal<MT4>::value )
1376 ConstIterator element( B.begin(i) );
1377 const ConstIterator
end( B.end(i) );
1379 for( ; element!=
end; ++element ) {
1380 C(i,element->index()) -= A(i,i) * element->value();
1385 const size_t jbegin( ( IsUpper<MT4>::value )
1386 ?( IsStrictlyUpper<MT4>::value ? i+1UL : i )
1388 const size_t jend( ( IsLower<MT4>::value )
1389 ?( IsStrictlyLower<MT4>::value ? i : i+1UL )
1393 for(
size_t j=jbegin; j<jend; ++j )
1395 ConstIterator element( B.begin(j) );
1396 const ConstIterator
end( B.end(j) );
1398 for( ; element!=
end; ++element ) {
1399 C(i,element->index()) -= A(i,j) * element->value();
1421 template<
typename MT >
1422 friend inline typename DisableIf< CanExploitSymmetry<MT,MT1,MT2> >::Type
1430 LT A(
serial( rhs.lhs_ ) );
1431 RT B(
serial( rhs.rhs_ ) );
1440 TDMatSMatMultExpr::selectColumnMajorSubAssignKernel( ~lhs, A, B );
1459 template<
typename MT3
1462 static inline typename EnableIf< UseDefaultKernel<MT3,MT4,MT5> >::Type
1463 selectColumnMajorSubAssignKernel( MT3& C,
const MT4& A,
const MT5& B )
1469 for(
size_t j=0UL; j<B.rows(); ++j )
1471 ConstIterator element( B.begin(j) );
1472 const ConstIterator
end( B.end(j) );
1474 if( IsDiagonal<MT4>::value )
1476 for( ; element!=
end; ++element ) {
1477 C(j,element->index()) -= A(j,j) * element->value();
1482 const size_t ibegin( ( IsLower<MT4>::value )
1483 ?( IsStrictlyLower<MT4>::value ? j+1UL : j )
1485 const size_t iend( ( IsUpper<MT4>::value )
1486 ?( IsStrictlyUpper<MT4>::value ? j : j+1UL )
1490 const size_t inum( iend - ibegin );
1491 const size_t ipos( ibegin + ( inum &
size_t(-4) ) );
1494 for( ; element!=
end; ++element ) {
1495 for( i=ibegin; i<ipos; i+=4UL ) {
1496 C(i ,element->index()) -= A(i ,j) * element->value();
1497 C(i+1UL,element->index()) -= A(i+1UL,j) * element->value();
1498 C(i+2UL,element->index()) -= A(i+2UL,j) * element->value();
1499 C(i+3UL,element->index()) -= A(i+3UL,j) * element->value();
1501 for( ; i<iend; ++i ) {
1502 C(i,element->index()) -= A(i,j) * element->value();
1525 template<
typename MT3
1528 static inline typename EnableIf< UseOptimizedKernel<MT3,MT4,MT5> >::Type
1529 selectColumnMajorSubAssignKernel( MT3& C,
const MT4& A,
const MT5& B )
1535 for(
size_t j=0UL; j<B.rows(); ++j )
1537 ConstIterator element( B.begin(j) );
1538 const ConstIterator
end( B.end(j) );
1540 const size_t nonzeros( B.nonZeros(j) );
1541 const size_t kpos( nonzeros &
size_t(-4) );
1544 const size_t ibegin( ( IsLower<MT4>::value )
1545 ?( IsStrictlyLower<MT4>::value ? j+1UL : j )
1547 const size_t iend( ( IsUpper<MT4>::value )
1548 ?( IsStrictlyUpper<MT4>::value ? j : j+1UL )
1552 const size_t inum( iend - ibegin );
1553 const size_t ipos( ibegin + ( inum &
size_t(-4) ) );
1556 for(
size_t k=0UL; k<kpos; k+=4UL )
1558 const size_t j1( element->index() );
1559 const ET2 v1( element->value() );
1561 const size_t j2( element->index() );
1562 const ET2 v2( element->value() );
1564 const size_t j3( element->index() );
1565 const ET2 v3( element->value() );
1567 const size_t j4( element->index() );
1568 const ET2 v4( element->value() );
1573 for( i=ibegin; i<ipos; i+=4UL ) {
1574 C(i ,j1) -= A(i ,j) * v1;
1575 C(i+1UL,j1) -= A(i+1UL,j) * v1;
1576 C(i+2UL,j1) -= A(i+2UL,j) * v1;
1577 C(i+3UL,j1) -= A(i+3UL,j) * v1;
1578 C(i ,j2) -= A(i ,j) * v2;
1579 C(i+1UL,j2) -= A(i+1UL,j) * v2;
1580 C(i+2UL,j2) -= A(i+2UL,j) * v2;
1581 C(i+3UL,j2) -= A(i+3UL,j) * v2;
1582 C(i ,j3) -= A(i ,j) * v3;
1583 C(i+1UL,j3) -= A(i+1UL,j) * v3;
1584 C(i+2UL,j3) -= A(i+2UL,j) * v3;
1585 C(i+3UL,j3) -= A(i+3UL,j) * v3;
1586 C(i ,j4) -= A(i ,j) * v4;
1587 C(i+1UL,j4) -= A(i+1UL,j) * v4;
1588 C(i+2UL,j4) -= A(i+2UL,j) * v4;
1589 C(i+3UL,j4) -= A(i+3UL,j) * v4;
1591 for( ; i<iend; ++i ) {
1592 C(i,j1) -= A(i,j) * v1;
1593 C(i,j2) -= A(i,j) * v2;
1594 C(i,j3) -= A(i,j) * v3;
1595 C(i,j4) -= A(i,j) * v4;
1599 for( ; element!=
end; ++element )
1601 const size_t j1( element->index() );
1602 const ET2 v1( element->value() );
1604 for( i=ibegin; i<ipos; i+=4UL ) {
1605 C(i ,j1) -= A(i ,j) * v1;
1606 C(i+1UL,j1) -= A(i+1UL,j) * v1;
1607 C(i+2UL,j1) -= A(i+2UL,j) * v1;
1608 C(i+3UL,j1) -= A(i+3UL,j) * v1;
1610 for( ; i<iend; ++i ) {
1611 C(i,j1) -= A(i,j) * v1;
1635 template<
typename MT >
1636 friend inline typename EnableIf< CanExploitSymmetry<MT,MT1,MT2> >::Type
1664 template<
typename MT >
1665 friend inline typename EnableIf< CanExploitSymmetry<MT,MT1,MT2> >::Type
1708 template<
typename MT
1710 friend inline typename EnableIf< IsEvaluationRequired<MT,MT1,MT2> >::Type
1749 template<
typename MT
1751 friend inline typename EnableIf< IsEvaluationRequired<MT,MT1,MT2> >::Type
1756 typedef typename SelectType< SO, ResultType, OppositeType >::Type TmpType;
1768 const TmpType tmp( rhs );
1789 template<
typename MT >
1790 friend inline typename EnableIf< CanExploitSymmetry<MT,MT1,MT2> >::Type
1820 template<
typename MT >
1821 friend inline typename EnableIf< CanExploitSymmetry<MT,MT1,MT2> >::Type
1850 template<
typename MT
1852 friend inline typename EnableIf< IsEvaluationRequired<MT,MT1,MT2> >::Type
1890 template<
typename MT >
1891 friend inline typename EnableIf< CanExploitSymmetry<MT,MT1,MT2> >::Type
1919 template<
typename MT >
1920 friend inline typename EnableIf< CanExploitSymmetry<MT,MT1,MT2> >::Type
1955 template<
typename MT
1957 friend inline typename EnableIf< IsEvaluationRequired<MT,MT1,MT2> >::Type
1995 template<
typename MT >
1996 friend inline typename EnableIf< CanExploitSymmetry<MT,MT1,MT2> >::Type
2026 template<
typename MT >
2027 friend inline typename EnableIf< CanExploitSymmetry<MT,MT1,MT2> >::Type
2103 template<
typename T1
2105 inline const TDMatSMatMultExpr<T1,T2>
2111 throw std::invalid_argument(
"Matrix sizes do not match" );
2128 template<
typename MT1,
typename MT2 >
2146 template<
typename MT1,
typename MT2 >
2148 :
public Columns<MT2>
2164 template<
typename MT1,
typename MT2 >
2166 :
public IsTrue< And< IsLower<MT1>, IsLower<MT2> >::value >
2182 template<
typename MT1,
typename MT2 >
2184 :
public IsTrue< And< IsUniLower<MT1>, IsUniLower<MT2> >::value >
2200 template<
typename MT1,
typename MT2 >
2202 :
public IsTrue< Or< And< IsStrictlyLower<MT1>, IsLower<MT2> >
2203 , And< IsStrictlyLower<MT2>, IsLower<MT1> > >::value >
2219 template<
typename MT1,
typename MT2 >
2221 :
public IsTrue< And< IsUpper<MT1>, IsUpper<MT2> >::value >
2237 template<
typename MT1,
typename MT2 >
2239 :
public IsTrue< And< IsUniUpper<MT1>, IsUniUpper<MT2> >::value >
2255 template<
typename MT1,
typename MT2 >
2257 :
public IsTrue< Or< And< IsStrictlyUpper<MT1>, IsUpper<MT2> >
2258 , And< IsStrictlyUpper<MT2>, IsUpper<MT1> > >::value >
2274 template<
typename MT1,
typename MT2,
typename VT >
2279 typedef typename SelectType< IsDenseMatrix<MT1>::value && IsColumnMajorMatrix<MT1>::value &&
2280 IsSparseMatrix<MT2>::value && IsRowMajorMatrix<MT2>::value &&
2281 IsDenseVector<VT>::value && IsColumnVector<VT>::value
2282 ,
typename TDMatDVecMultExprTrait< MT1, typename SMatDVecMultExprTrait<MT2,VT>::Type >::Type
2283 , INVALID_TYPE >::Type Type;
2292 template<
typename MT1,
typename MT2,
typename VT >
2297 typedef typename SelectType< IsDenseMatrix<MT1>::value && IsColumnMajorMatrix<MT1>::value &&
2298 IsSparseMatrix<MT2>::value && IsRowMajorMatrix<MT2>::value &&
2299 IsSparseVector<VT>::value && IsColumnVector<VT>::value
2300 ,
typename TDMatSVecMultExprTrait< MT1, typename SMatSVecMultExprTrait<MT2,VT>::Type >::Type
2301 , INVALID_TYPE >::Type Type;
2310 template<
typename VT,
typename MT1,
typename MT2 >
2315 typedef typename SelectType< IsDenseVector<VT>::value && IsRowVector<VT>::value &&
2316 IsDenseMatrix<MT1>::value && IsColumnMajorMatrix<MT1>::value &&
2317 IsSparseMatrix<MT2>::value && IsRowMajorMatrix<MT2>::value
2318 ,
typename TDMatDVecMultExprTrait< MT1, typename SMatDVecMultExprTrait<MT2,VT>::Type >::Type
2319 , INVALID_TYPE >::Type Type;
2328 template<
typename VT,
typename MT1,
typename MT2 >
2333 typedef typename SelectType< IsSparseVector<VT>::value && IsRowVector<VT>::value &&
2334 IsDenseMatrix<MT1>::value && IsColumnMajorMatrix<MT1>::value &&
2335 IsSparseMatrix<MT2>::value && IsRowMajorMatrix<MT2>::value
2336 ,
typename TDVecSMatMultExprTrait< typename TSVecTDMatMultExprTrait<VT,MT1>::Type, MT2 >::Type
2337 , INVALID_TYPE >::Type Type;
2346 template<
typename MT1,
typename MT2,
bool AF >
2351 typedef typename MultExprTrait< typename SubmatrixExprTrait<const MT1,AF>::Type
2352 ,
typename SubmatrixExprTrait<const MT2,AF>::Type >::Type Type;
2361 template<
typename MT1,
typename MT2 >
2366 typedef typename MultExprTrait< typename RowExprTrait<const MT1>::Type, MT2 >::Type Type;
2375 template<
typename MT1,
typename MT2 >
2380 typedef typename MultExprTrait< MT1, typename ColumnExprTrait<const MT2>::Type >::Type Type;
SelectType< evaluateLeft, const RT1, CT1 >::Type LT
Type for the assignment of the left-hand side dense matrix operand.
Definition: TDMatSMatMultExpr.h:220
const MT::ElementType max(const DenseMatrix< MT, SO > &dm)
Returns the largest element of the dense matrix.
Definition: DenseMatrix.h:1649
Compile time check whether the given type is a computational expression template.This type trait clas...
Definition: IsComputation.h:89
MT1::ResultType RT1
Result type of the left-hand side dense matrix expression.
Definition: TDMatSMatMultExpr.h:127
Header file for the SMatDVecMultExprTrait class template.
const ResultType CompositeType
Data type for composite expression templates.
Definition: TDMatSMatMultExpr.h:211
Header file for the Rows type trait.
Header file for the IsUniUpper type trait.
const DMatDMatMultExpr< T1, T2 > operator*(const DenseMatrix< T1, false > &lhs, const DenseMatrix< T2, false > &rhs)
Multiplication operator for the multiplication of two row-major dense matrices ( ).
Definition: DMatDMatMultExpr.h:8247
Compile time check for triangular matrix types.This type trait tests whether or not the given templat...
Definition: IsTriangular.h:105
Header file for basic type definitions.
BLAZE_ALWAYS_INLINE MT::Iterator end(Matrix< MT, SO > &matrix, size_t i)
Returns an iterator just past the last element of row/column i.
Definition: Matrix.h:258
Header file for the IsSparseMatrix type trait.
Efficient implementation of a compressed matrix.The CompressedMatrix class template is the represent...
Definition: CompressedMatrix.h:209
Header file for the IsDiagonal type trait.
#define BLAZE_CONSTRAINT_MUST_BE_DENSE_MATRIX_TYPE(T)
Constraint on the data type.In case the given data type T is not a dense, N-dimensional matrix type...
Definition: DenseMatrix.h:79
Header file for the ColumnExprTrait class template.
Header file for the IsColumnMajorMatrix type trait.
void reset(const DiagonalProxy< MT > &proxy)
Resetting the represented element to the default initial values.
Definition: DiagonalProxy.h:821
const This & CompositeType
Data type for composite expression templates.
Definition: CompressedMatrix.h:2507
Header file for the IsRowVector type trait.
Type ElementType
Type of the sparse matrix elements.
Definition: CompressedMatrix.h:261
Header file for the And class template.
Compile time check for lower triangular matrices.This type trait tests whether or not the given templ...
Definition: IsLower.h:90
size_t columns() const
Returns the current number of columns of the matrix.
Definition: TDMatSMatMultExpr.h:305
Header file for the TDVecSMatMultExprTrait class template.
const DMatSerialExpr< MT, SO > serial(const DenseMatrix< MT, SO > &dm)
Forces the serial evaluation of the given dense matrix expression dm.
Definition: DMatSerialExpr.h:699
Header file for the Computation base class.
Header file for the MatMatMultExpr base class.
Compile time check for upper triangular matrices.This type trait tests whether or not the given templ...
Definition: IsUpper.h:90
const ElementType ReturnType
Return type for expression template evaluations.
Definition: TDMatSMatMultExpr.h:210
Expression object for transpose dense matrix-sparse matrix multiplications.The TDMatSMatMultExpr clas...
Definition: Forward.h:128
Header file for the IsUniLower type trait.
LeftOperand leftOperand() const
Returns the left-hand side transpose dense matrix operand.
Definition: TDMatSMatMultExpr.h:315
bool isAligned() const
Returns whether the operands of the expression are properly aligned in memory.
Definition: TDMatSMatMultExpr.h:359
Base class for dense matrices.The DenseMatrix class is a base class for all dense matrix classes...
Definition: DenseMatrix.h:70
Base class for sparse matrices.The SparseMatrix class is a base class for all sparse matrix classes...
Definition: Forward.h:107
bool isDefault(const DiagonalProxy< MT > &proxy)
Returns whether the represented element is in default state.
Definition: DiagonalProxy.h:861
Constraint on the data type.
Constraint on the data type.
Constraint on the data type.
Header file for the MultExprTrait class template.
Compile time check to query the requirement to evaluate an expression.Via this type trait it is possi...
Definition: RequiresEvaluation.h:90
bool canSMPAssign() const
Returns whether the expression can be used in SMP assignments.
Definition: TDMatSMatMultExpr.h:369
RT2::ElementType ET2
Element type of the right-hand side sparse matrix expression.
Definition: TDMatSMatMultExpr.h:130
Compile time type selection.The SelectType class template selects one of the two given types T1 and T...
Definition: SelectType.h:59
Header file for the DisableIf class template.
Header file for the multiplication trait.
Header file for the IsStrictlyUpper type trait.
SelectType< IsExpression< MT2 >::value, const MT2, const MT2 & >::Type RightOperand
Composite type of the right-hand side sparse matrix expression.
Definition: TDMatSMatMultExpr.h:217
Header file for the IsSymmetric type trait.
Namespace of the Blaze C++ math library.
Definition: Blaze.h:57
#define BLAZE_CONSTRAINT_MUST_BE_COLUMN_MAJOR_MATRIX_TYPE(T)
Constraint on the data type.In case the given data type T is not a column-major dense or sparse matri...
Definition: StorageOrder.h:161
Header file for the TSVecTDMatMultExprTrait class template.
const Element * ConstIterator
Iterator over constant elements.
Definition: CompressedMatrix.h:2511
Header file for the Or class template.
Header file for the TDMatSVecMultExprTrait class template.
const MT::ElementType min(const DenseMatrix< MT, SO > &dm)
Returns the smallest element of the dense matrix.
Definition: DenseMatrix.h:1602
Header file for the DenseMatrix base class.
BLAZE_ALWAYS_INLINE void assign(Matrix< MT1, SO1 > &lhs, const Matrix< MT2, SO2 > &rhs)
Default implementation of the assignment of a matrix to a matrix.
Definition: Matrix.h:635
Header file for the Columns type trait.
MT2::CompositeType CT2
Composite type of the right-hand side sparse matrix expression.
Definition: TDMatSMatMultExpr.h:132
Header file for the IsLower type trait.
ResultType::ElementType ElementType
Resulting element type.
Definition: TDMatSMatMultExpr.h:209
RightOperand rhs_
Right-hand side sparse matrix of the multiplication expression.
Definition: TDMatSMatMultExpr.h:377
LeftOperand lhs_
Left-hand side dense matrix of the multiplication expression.
Definition: TDMatSMatMultExpr.h:376
Header file for the SMatSVecMultExprTrait class template.
#define BLAZE_CONSTRAINT_MUST_BE_REFERENCE_TYPE(T)
Constraint on the data type.In case the given data type T is not a reference type, a compilation error is created.
Definition: Reference.h:78
Header file for the IsTriangular type trait.
Constraints on the storage order of matrix types.
bool isAliased(const T *alias) const
Returns whether the expression is aliased with the given address alias.
Definition: TDMatSMatMultExpr.h:349
Compile time check for strictly upper triangular matrices.This type trait tests whether or not the gi...
Definition: IsStrictlyUpper.h:86
Type ElementType
Type of the sparse matrix elements.
Definition: CompressedMatrix.h:2505
ReturnType operator()(size_t i, size_t j) const
2D-access to the matrix elements.
Definition: TDMatSMatMultExpr.h:256
ResultType::OppositeType OppositeType
Result type with opposite storage order for expression template evaluations.
Definition: TDMatSMatMultExpr.h:207
Header file for the SelectType class template.
Header file for the RowExprTrait class template.
Header file for all forward declarations for expression class templates.
Header file for the IsDenseMatrix type trait.
MultTrait< RT1, RT2 >::Type ResultType
Result type for expression template evaluations.
Definition: TDMatSMatMultExpr.h:206
TDMatSMatMultExpr(const MT1 &lhs, const MT2 &rhs)
Constructor for the TDMatSMatMultExpr class.
Definition: TDMatSMatMultExpr.h:241
Header file for the EnableIf class template.
Header file for the IsStrictlyLower type trait.
Header file for the serial shim.
#define BLAZE_CONSTRAINT_MUST_FORM_VALID_MATMATMULTEXPR(T1, T2)
Constraint on the data type.In case the given data types T1 and T2 do not form a valid matrix/matrix ...
Definition: MatMatMultExpr.h:165
EnableIf< IsDenseMatrix< MT1 > >::Type smpSubAssign(Matrix< MT1, SO1 > &lhs, const Matrix< MT2, SO2 > &rhs)
Default implementation of the SMP subtraction assignment of a matrix to dense matrix.
Definition: DenseMatrix.h:160
Header file for the IsSparseVector type trait.
#define BLAZE_CONSTRAINT_MUST_NOT_BE_SYMMETRIC_MATRIX_TYPE(T)
Constraint on the data type.In case the given data type T is a symmetric matrix type, a compilation error is created.
Definition: Symmetric.h:116
Header file for the SubmatrixExprTrait class template.
#define BLAZE_CONSTRAINT_MUST_BE_ROW_MAJOR_MATRIX_TYPE(T)
Constraint on the data type.In case the given data type T is not a row-major dense or sparse matrix t...
Definition: StorageOrder.h:81
ResultType::TransposeType TransposeType
Transpose type for expression template evaluations.
Definition: TDMatSMatMultExpr.h:208
bool canAlias(const T *alias) const
Returns whether the expression can alias with the given address alias.
Definition: TDMatSMatMultExpr.h:337
Header file for run time assertion macros.
EnableIf< IsDenseMatrix< MT1 > >::Type smpAssign(Matrix< MT1, SO1 > &lhs, const Matrix< MT2, SO2 > &rhs)
Default implementation of the SMP assignment of a matrix to a dense matrix.
Definition: DenseMatrix.h:98
Utility type for generic codes.
Base template for the MultTrait class.
Definition: MultTrait.h:150
BLAZE_ALWAYS_INLINE void addAssign(Matrix< MT1, SO1 > &lhs, const Matrix< MT2, SO2 > &rhs)
Default implementation of the addition assignment of a matrix to a matrix.
Definition: Matrix.h:742
SelectType< IsExpression< MT1 >::value, const MT1, const MT1 & >::Type LeftOperand
Composite type of the left-hand side dense matrix expression.
Definition: TDMatSMatMultExpr.h:214
Substitution Failure Is Not An Error (SFINAE) class.The EnableIf class template is an auxiliary tool ...
Definition: EnableIf.h:184
const size_t SMP_TDMATSMATMULT_THRESHOLD
SMP column-major dense matrix/row-major sparse matrix multiplication threshold.This threshold specifi...
Definition: Thresholds.h:972
Header file for the reset shim.
Header file for the isDefault shim.
Constraint on the data type.
Substitution Failure Is Not An Error (SFINAE) class.The DisableIf class template is an auxiliary tool...
Definition: DisableIf.h:184
#define BLAZE_CONSTRAINT_MATRICES_MUST_HAVE_SAME_STORAGE_ORDER(T1, T2)
Constraint on the data type.In case either of the two given data types T1 or T2 is not a matrix type ...
Definition: StorageOrder.h:283
Header file for the IsDenseVector type trait.
Compile time check for strictly lower triangular matrices.This type trait tests whether or not the gi...
Definition: IsStrictlyLower.h:86
MT2::ResultType RT2
Result type of the right-hand side sparse matrix expression.
Definition: TDMatSMatMultExpr.h:128
RightOperand rightOperand() const
Returns the right-hand side sparse matrix operand.
Definition: TDMatSMatMultExpr.h:325
Header file for the IsRowMajorMatrix type trait.
size_t rows() const
Returns the current number of rows of the matrix.
Definition: TDMatSMatMultExpr.h:295
const DMatTransExpr< MT,!SO > trans(const DenseMatrix< MT, SO > &dm)
Calculation of the transpose of the given dense matrix.
Definition: DMatTransExpr.h:937
TDMatSMatMultExpr< MT1, MT2 > This
Type of this TDMatSMatMultExpr instance.
Definition: TDMatSMatMultExpr.h:205
Header file for the IsComputation type trait class.
EnableIf< IsDenseMatrix< MT1 > >::Type smpAddAssign(Matrix< MT1, SO1 > &lhs, const Matrix< MT2, SO2 > &rhs)
Default implementation of the SMP addition assignment of a matrix to a dense matrix.
Definition: DenseMatrix.h:129
Header file for the TDMatDVecMultExprTrait class template.
#define BLAZE_FUNCTION_TRACE
Function trace macro.This macro can be used to reliably trace function calls. In case function tracin...
Definition: FunctionTrace.h:157
This ResultType
Result type for expression template evaluations.
Definition: CompressedMatrix.h:2502
Header file for the IsTrue value trait.
MT1::CompositeType CT1
Composite type of the left-hand side dense matrix expression.
Definition: TDMatSMatMultExpr.h:131
RT1::ElementType ET1
Element type of the left-hand side dense matrix expression.
Definition: TDMatSMatMultExpr.h:129
SelectType< evaluateRight, const RT2, CT2 >::Type RT
Type for the assignment of the right-hand side sparse matrix operand.
Definition: TDMatSMatMultExpr.h:223
Header file for the IsUpper type trait.
Header file for the IsColumnVector type trait.
Constraint on the data type.
Header file for the IsResizable type trait.
Header file for the thresholds for matrix/vector and matrix/matrix multiplications.
#define BLAZE_INTERNAL_ASSERT(expr, msg)
Run time assertion macro for internal checks.In case of an invalid run time expression, the program execution is terminated. The BLAZE_INTERNAL_ASSERT macro can be disabled by setting the BLAZE_USER_ASSERTION flag to zero or by defining NDEBUG during the compilation.
Definition: Assert.h:101
Header file for the TDVecTDMatMultExprTrait class template.
#define BLAZE_CONSTRAINT_MUST_BE_SPARSE_MATRIX_TYPE(T)
Constraint on the data type.In case the given data type T is not a sparse, N-dimensional matrix type...
Definition: SparseMatrix.h:79
Header file for the IsExpression type trait class.
Header file for the FunctionTrace class.
BLAZE_ALWAYS_INLINE void subAssign(Matrix< MT1, SO1 > &lhs, const Matrix< MT2, SO2 > &rhs)
Default implementation of the subtraction assignment of a matrix to matrix.
Definition: Matrix.h:849