35 #ifndef _BLAZE_MATH_EXPRESSIONS_TDMATTSMATMULTEXPR_H_ 36 #define _BLAZE_MATH_EXPRESSIONS_TDMATTSMATMULTEXPR_H_ 123 template<
typename MT1
129 class TDMatTSMatMultExpr
130 :
public MatMatMultExpr< DenseMatrix< TDMatTSMatMultExpr<MT1,MT2,SF,HF,LF,UF>, true > >
131 ,
private Computation
145 static constexpr
bool evaluateLeft = ( IsComputation_v<MT1> || RequiresEvaluation_v<MT1> );
150 static constexpr
bool evaluateRight = ( IsComputation_v<MT2> || RequiresEvaluation_v<MT2> );
154 static constexpr
bool SYM = ( SF && !( HF || LF || UF ) );
155 static constexpr
bool HERM = ( HF && !( LF || UF ) );
156 static constexpr
bool LOW = ( LF || ( ( SF || HF ) && UF ) );
157 static constexpr
bool UPP = ( UF || ( ( SF || HF ) && LF ) );
166 template<
typename T1,
typename T2,
typename T3 >
176 template<
typename T1,
typename T2,
typename T3 >
177 static constexpr
bool UseVectorizedKernel_v =
178 ( useOptimizedKernels &&
180 T1::simdEnabled && T2::simdEnabled &&
181 IsColumnMajorMatrix_v<T1> &&
182 IsSIMDCombinable_v< ElementType_t<T1>
196 template<
typename T1,
typename T2,
typename T3 >
197 static constexpr
bool UseOptimizedKernel_v =
198 ( useOptimizedKernels &&
199 !UseVectorizedKernel_v<T1,T2,T3> &&
201 !IsResizable_v< ElementType_t<T1> > &&
202 !IsResizable_v<ET2> );
211 template<
typename T1,
typename T2,
typename T3 >
212 static constexpr
bool UseDefaultKernel_v =
213 ( !UseVectorizedKernel_v<T1,T2,T3> && !UseOptimizedKernel_v<T1,T2,T3> );
280 ( !IsDiagonal_v<MT1> &&
282 HasSIMDAdd_v<ET1,ET2> &&
283 HasSIMDMult_v<ET1,ET2> );
320 if( IsDiagonal_v<MT1> ) {
323 else if( IsDiagonal_v<MT2> ) {
326 else if( IsTriangular_v<MT1> || IsTriangular_v<MT2> ) {
327 const size_t begin( ( IsUpper_v<MT1> )
328 ?( ( IsLower_v<MT2> )
329 ?(
max( ( IsStrictlyUpper_v<MT1> ? i+1UL : i )
330 , ( IsStrictlyLower_v<MT2> ? j+1UL : j ) ) )
331 :( IsStrictlyUpper_v<MT1> ? i+1UL : i ) )
332 :( ( IsLower_v<MT2> )
333 ?( IsStrictlyLower_v<MT2> ? j+1UL : j )
335 const size_t end( ( IsLower_v<MT1> )
336 ?( ( IsUpper_v<MT2> )
337 ?(
min( ( IsStrictlyLower_v<MT1> ? i : i+1UL )
338 , ( IsStrictlyUpper_v<MT2> ? j : j+1UL ) ) )
339 :( IsStrictlyLower_v<MT1> ? i : i+1UL ) )
340 :( ( IsUpper_v<MT2> )
341 ?( IsStrictlyUpper_v<MT2> ? j : j+1UL )
342 :(
lhs_.columns() ) ) );
366 if( i >=
lhs_.rows() ) {
369 if( j >=
rhs_.columns() ) {
381 inline size_t rows() const noexcept {
392 return rhs_.columns();
422 template<
typename T >
423 inline bool canAlias(
const T* alias )
const noexcept {
424 return (
lhs_.isAliased( alias ) ||
rhs_.isAliased( alias ) );
434 template<
typename T >
435 inline bool isAliased(
const T* alias )
const noexcept {
436 return (
lhs_.isAliased( alias ) ||
rhs_.isAliased( alias ) );
446 return lhs_.isAligned();
456 return (
rows() *
columns() >= SMP_TDMATTSMATMULT_THRESHOLD ) && !IsDiagonal_v<MT1>;
479 template<
typename MT
498 TDMatTSMatMultExpr::selectAssignKernel( ~lhs, A, B );
517 template<
typename MT3
520 static inline auto selectAssignKernel( MT3& C,
const MT4& A,
const MT5& B )
523 const size_t block( IsColumnMajorMatrix_v<MT3> || IsDiagonal_v<MT4> ? A.rows() : 64UL );
527 for(
size_t ii=0UL; ii<A.rows(); ii+=block )
529 const size_t itmp(
min( ii+block, A.rows() ) );
531 for(
size_t j=0UL; j<B.columns(); ++j )
533 auto element( B.begin(j) );
534 const auto end( B.end(j) );
536 for( ; element!=
end; ++element )
538 const size_t j1( element->index() );
540 if( IsDiagonal_v<MT4> )
542 C(j1,j) = A(j1,j1) * element->value();
546 const size_t ibegin( ( IsLower_v<MT4> )
548 ?(
max( j, ii, ( IsStrictlyLower_v<MT4> ? j1+1UL : j1 ) ) )
549 :(
max( ii, ( IsStrictlyLower_v<MT4> ? j1+1UL : j1 ) ) ) )
550 :(
LOW ?
max(j,ii) : ii ) );
551 const size_t iend( ( IsUpper_v<MT4> )
553 ?(
min( j+1UL, itmp, ( IsStrictlyUpper_v<MT4> ? j1 : j1+1UL ) ) )
554 :(
min( itmp, ( IsStrictlyUpper_v<MT4> ? j1 : j1+1UL ) ) ) )
557 if( (
SYM ||
HERM ||
LOW ||
UPP || IsTriangular_v<MT4> ) && ( ibegin >= iend ) )
562 for(
size_t i=ibegin; i<iend; ++i ) {
564 C(i,j) = A(i,j1) * element->value();
566 C(i,j) += A(i,j1) * element->value();
574 for(
size_t j=0UL; j<B.columns(); ++j ) {
575 for(
size_t i=j+1UL; i<A.rows(); ++i ) {
576 C(i,j) =
HERM ?
conj( C(j,i) ) : C(j,i);
598 template<
typename MT3
601 static inline auto selectAssignKernel( MT3& C,
const MT4& A,
const MT5& B )
602 -> EnableIf_t< UseOptimizedKernel_v<MT3,MT4,MT5> >
604 const size_t block( IsColumnMajorMatrix_v<MT3> ? A.rows() : 64UL );
608 for(
size_t ii=0UL; ii<A.rows(); ii+=block )
610 const size_t itmp(
min( ii+block, A.rows() ) );
612 for(
size_t j=0UL; j<B.columns(); ++j )
614 const auto end( B.end(j) );
615 auto element( B.begin(j) );
617 const size_t nonzeros( B.nonZeros(j) );
618 const size_t kpos( nonzeros &
size_t(-4) );
621 for(
size_t k=0UL; k<kpos; k+=4UL )
623 const size_t j1( element->index() );
624 const ET2 v1( element->value() );
626 const size_t j2( element->index() );
627 const ET2 v2( element->value() );
629 const size_t j3( element->index() );
630 const ET2 v3( element->value() );
632 const size_t j4( element->index() );
633 const ET2 v4( element->value() );
638 const size_t ibegin( ( IsLower_v<MT4> )
640 ?(
max( j, ii, ( IsStrictlyLower_v<MT4> ? j1+1UL : j1 ) ) )
641 :(
max( ii, ( IsStrictlyLower_v<MT4> ? j1+1UL : j1 ) ) ) )
642 :(
LOW ?
max(j,ii) : ii ) );
643 const size_t iend( ( IsUpper_v<MT4> )
645 ?(
min( j+1UL, itmp, ( IsStrictlyUpper_v<MT4> ? j4 : j4+1UL ) ) )
646 :(
min( itmp, ( IsStrictlyUpper_v<MT4> ? j4 : j4+1UL ) ) ) )
649 if( (
SYM ||
HERM ||
LOW ||
UPP || IsTriangular_v<MT4> ) && ( ibegin >= iend ) )
654 const size_t inum( iend - ibegin );
655 const size_t ipos( ibegin + ( inum &
size_t(-4) ) );
658 for(
size_t i=ibegin; i<ipos; i+=4UL ) {
659 C(i ,j) += A(i ,j1) * v1 + A(i ,j2) * v2 + A(i ,j3) * v3 + A(i ,j4) * v4;
660 C(i+1UL,j) += A(i+1UL,j1) * v1 + A(i+1UL,j2) * v2 + A(i+1UL,j3) * v3 + A(i+1UL,j4) * v4;
661 C(i+2UL,j) += A(i+2UL,j1) * v1 + A(i+2UL,j2) * v2 + A(i+2UL,j3) * v3 + A(i+2UL,j4) * v4;
662 C(i+3UL,j) += A(i+3UL,j1) * v1 + A(i+3UL,j2) * v2 + A(i+3UL,j3) * v3 + A(i+3UL,j4) * v4;
664 for(
size_t i=ipos; i<iend; ++i ) {
665 C(i,j) += A(i,j1) * v1 + A(i,j2) * v2 + A(i,j3) * v3 + A(i,j4) * v4;
669 for( ; element!=
end; ++element )
671 const size_t j1( element->index() );
672 const ET2 v1( element->value() );
674 const size_t ibegin( ( IsLower_v<MT4> )
676 ?(
max( j, ii, ( IsStrictlyLower_v<MT4> ? j1+1UL : j1 ) ) )
677 :(
max( ii, ( IsStrictlyLower_v<MT4> ? j1+1UL : j1 ) ) ) )
678 :(
LOW ?
max(j,ii) : ii ) );
679 const size_t iend( ( IsUpper_v<MT4> )
681 ?(
min( j+1UL, itmp, ( IsStrictlyUpper_v<MT4> ? j1 : j1+1UL ) ) )
682 :(
min( itmp, ( IsStrictlyUpper_v<MT4> ? j1 : j1+1UL ) ) ) )
685 if( (
SYM ||
HERM ||
LOW ||
UPP || IsTriangular_v<MT4> ) && ( ibegin >= iend ) )
690 const size_t inum( iend - ibegin );
691 const size_t ipos( ibegin + ( inum &
size_t(-4) ) );
694 for(
size_t i=ibegin; i<ipos; i+=4UL ) {
695 C(i ,j) += A(i ,j1) * v1;
696 C(i+1UL,j) += A(i+1UL,j1) * v1;
697 C(i+2UL,j) += A(i+2UL,j1) * v1;
698 C(i+3UL,j) += A(i+3UL,j1) * v1;
700 for(
size_t i=ipos; i<iend; ++i ) {
701 C(i,j) += A(i,j1) * v1;
708 for(
size_t j=0UL; j<B.columns(); ++j ) {
709 for(
size_t i=j+1UL; i<A.rows(); ++i ) {
710 C(i,j) =
HERM ?
conj( C(j,i) ) : C(j,i);
732 template<
typename MT3
735 static inline auto selectAssignKernel( MT3& C,
const MT4& A,
const MT5& B )
736 -> EnableIf_t< UseVectorizedKernel_v<MT3,MT4,MT5> >
738 constexpr
bool remainder( !IsPadded_v<MT3> || !IsPadded_v<MT4> );
742 for(
size_t j=0UL; j<B.columns(); ++j )
744 const auto end( B.end(j) );
745 auto element( B.begin(j) );
747 const size_t nonzeros( B.nonZeros(j) );
748 const size_t kpos( nonzeros &
size_t(-4) );
751 for(
size_t k=0UL; k<kpos; k+=4UL )
753 const size_t j1( element->index() );
754 const ET2 v1( element->value() );
756 const size_t j2( element->index() );
757 const ET2 v2( element->value() );
759 const size_t j3( element->index() );
760 const ET2 v3( element->value() );
762 const size_t j4( element->index() );
763 const ET2 v4( element->value() );
773 const size_t ibegin( ( IsLower_v<MT4> )
774 ?( ( IsStrictlyLower_v<MT4> )
778 const size_t iend( ( IsUpper_v<MT4> )
779 ?( ( IsStrictlyUpper_v<MT4> )
785 const size_t ipos( remainder ? ( iend &
size_t(-
SIMDSIZE) ) : iend );
791 C.store( i, j, C.load(i,j) + A.load(i,j1) * xmm1 + A.load(i,j2) * xmm2 + A.load(i,j3) * xmm3 + A.load(i,j4) * xmm4 );
793 for( ; remainder && i<iend; ++i ) {
794 C(i,j) += A(i,j1) * v1 + A(i,j2) * v2 + A(i,j3) * v3 + A(i,j4) * v4;
798 for( ; element!=
end; ++element )
800 const size_t j1( element->index() );
801 const ET2 v1( element->value() );
805 const size_t ibegin( ( IsLower_v<MT4> )
806 ?( ( IsStrictlyLower_v<MT4> )
810 const size_t iend( ( IsUpper_v<MT4> )
811 ?( ( IsStrictlyUpper_v<MT4> )
817 const size_t ipos( remainder ? ( iend &
size_t(-
SIMDSIZE) ) : iend );
823 C.store( i, j, C.load(i,j) + A.load(i,j1) * xmm1 );
825 for( ; remainder && i<iend; ++i ) {
826 C(i,j) += A(i,j1) * v1;
832 for(
size_t j=0UL; j<B.columns(); ++j ) {
833 for(
size_t i=j+1UL; i<A.rows(); ++i ) {
834 C(i,j) =
HERM ?
conj( C(j,i) ) : C(j,i);
855 template<
typename MT
861 using TmpType = If_t< SO, ResultType, OppositeType >;
873 const ForwardFunctor fwd;
875 const TmpType tmp(
serial( rhs ) );
876 assign( ~lhs, fwd( tmp ) );
894 template<
typename MT
896 friend inline void addAssign( DenseMatrix<MT,SO>& lhs,
const TDMatTSMatMultExpr& rhs )
913 TDMatTSMatMultExpr::selectAddAssignKernel( ~lhs, A, B );
932 template<
typename MT3
935 static inline auto selectAddAssignKernel( MT3& C,
const MT4& A,
const MT5& B )
936 -> EnableIf_t< UseDefaultKernel_v<MT3,MT4,MT5> >
938 const size_t block( IsColumnMajorMatrix_v<MT3> || IsDiagonal_v<MT4> ? A.rows() : 64UL );
940 for(
size_t ii=0UL; ii<A.rows(); ii+=block )
942 const size_t itmp(
min( ii+block, A.rows() ) );
944 for(
size_t j=0UL; j<B.columns(); ++j )
946 auto element( B.begin(j) );
947 const auto end( B.end(j) );
949 for( ; element!=
end; ++element )
951 const size_t j1( element->index() );
953 if( IsDiagonal_v<MT4> )
955 C(j1,j) += A(j1,j1) * element->value();
959 const size_t ibegin( ( IsLower_v<MT4> )
961 ?(
max( j, ii, ( IsStrictlyLower_v<MT4> ? j1+1UL : j1 ) ) )
962 :(
max( ii, ( IsStrictlyLower_v<MT4> ? j1+1UL : j1 ) ) ) )
963 :(
LOW ?
max(j,ii) : ii ) );
964 const size_t iend( ( IsUpper_v<MT4> )
966 ?(
min( j+1UL, itmp, ( IsStrictlyUpper_v<MT4> ? j1 : j1+1UL ) ) )
967 :(
min( itmp, ( IsStrictlyUpper_v<MT4> ? j1 : j1+1UL ) ) ) )
968 :(
UPP ?
min(j+1UL,itmp) : itmp ) );
970 if( (
LOW ||
UPP || IsTriangular_v<MT4> ) && ( ibegin >= iend ) )
975 const size_t inum( iend - ibegin );
976 const size_t ipos( ibegin + ( inum &
size_t(-4) ) );
979 for(
size_t i=ibegin; i<ipos; i+=4UL ) {
980 C(i ,j) += A(i ,j1) * element->value();
981 C(i+1UL,j) += A(i+1UL,j1) * element->value();
982 C(i+2UL,j) += A(i+2UL,j1) * element->value();
983 C(i+3UL,j) += A(i+3UL,j1) * element->value();
985 for(
size_t i=ipos; i<iend; ++i ) {
986 C(i,j) += A(i,j1) * element->value();
1010 template<
typename MT3
1013 static inline auto selectAddAssignKernel( MT3& C,
const MT4& A,
const MT5& B )
1014 -> EnableIf_t< UseOptimizedKernel_v<MT3,MT4,MT5> >
1016 const size_t block( IsColumnMajorMatrix_v<MT3> ? A.rows() : 64UL );
1018 for(
size_t ii=0UL; ii<A.rows(); ii+=block )
1020 const size_t itmp(
min( ii+block, A.rows() ) );
1022 for(
size_t j=0UL; j<B.columns(); ++j )
1024 const auto end( B.end(j) );
1025 auto element( B.begin(j) );
1027 const size_t nonzeros( B.nonZeros(j) );
1028 const size_t kpos( nonzeros &
size_t(-4) );
1031 for(
size_t k=0UL; k<kpos; k+=4UL )
1033 const size_t j1( element->index() );
1034 const ET2 v1( element->value() );
1036 const size_t j2( element->index() );
1037 const ET2 v2( element->value() );
1039 const size_t j3( element->index() );
1040 const ET2 v3( element->value() );
1042 const size_t j4( element->index() );
1043 const ET2 v4( element->value() );
1048 const size_t ibegin( ( IsLower_v<MT4> )
1050 ?(
max( j, ii, ( IsStrictlyLower_v<MT4> ? j1+1UL : j1 ) ) )
1051 :(
max( ii, ( IsStrictlyLower_v<MT4> ? j1+1UL : j1 ) ) ) )
1052 :(
LOW ?
max(j,ii) : ii ) );
1053 const size_t iend( ( IsUpper_v<MT4> )
1055 ?(
min( j+1UL, itmp, ( IsStrictlyUpper_v<MT4> ? j4 : j4+1UL ) ) )
1056 :(
min( itmp, ( IsStrictlyUpper_v<MT4> ? j4 : j4+1UL ) ) ) )
1057 :(
UPP ?
min(j+1UL,itmp) : itmp ) );
1059 if( (
LOW ||
UPP || IsTriangular_v<MT4> ) && ( ibegin >= iend ) )
1064 const size_t inum( iend - ibegin );
1065 const size_t ipos( ibegin + ( inum &
size_t(-4) ) );
1068 for(
size_t i=ibegin; i<ipos; i+=4UL ) {
1069 C(i ,j) += A(i ,j1) * v1 + A(i ,j2) * v2 + A(i ,j3) * v3 + A(i ,j4) * v4;
1070 C(i+1UL,j) += A(i+1UL,j1) * v1 + A(i+1UL,j2) * v2 + A(i+1UL,j3) * v3 + A(i+1UL,j4) * v4;
1071 C(i+2UL,j) += A(i+2UL,j1) * v1 + A(i+2UL,j2) * v2 + A(i+2UL,j3) * v3 + A(i+2UL,j4) * v4;
1072 C(i+3UL,j) += A(i+3UL,j1) * v1 + A(i+3UL,j2) * v2 + A(i+3UL,j3) * v3 + A(i+3UL,j4) * v4;
1074 for(
size_t i=ipos; i<iend; ++i ) {
1075 C(i,j) += A(i,j1) * v1 + A(i,j2) * v2 + A(i,j3) * v3 + A(i,j4) * v4;
1079 for( ; element!=
end; ++element )
1081 const size_t j1( element->index() );
1082 const ET2 v1( element->value() );
1084 const size_t ibegin( ( IsLower_v<MT4> )
1086 ?(
max( j, ii, ( IsStrictlyLower_v<MT4> ? j1+1UL : j1 ) ) )
1087 :(
max( ii, ( IsStrictlyLower_v<MT4> ? j1+1UL : j1 ) ) ) )
1088 :(
LOW ?
max(j,ii) : ii ) );
1089 const size_t iend( ( IsUpper_v<MT4> )
1091 ?(
min( j+1UL, itmp, ( IsStrictlyUpper_v<MT4> ? j1 : j1+1UL ) ) )
1092 :(
min( itmp, ( IsStrictlyUpper_v<MT4> ? j1 : j1+1UL ) ) ) )
1093 :(
UPP ?
min(j+1UL,itmp) : itmp ) );
1095 if( (
LOW ||
UPP || IsTriangular_v<MT4> ) && ( ibegin >= iend ) )
1100 const size_t inum( iend - ibegin );
1101 const size_t ipos( ibegin + ( inum &
size_t(-4) ) );
1104 for(
size_t i=ibegin; i<ipos; i+=4UL ) {
1105 C(i ,j) += A(i ,j1) * v1;
1106 C(i+1UL,j) += A(i+1UL,j1) * v1;
1107 C(i+2UL,j) += A(i+2UL,j1) * v1;
1108 C(i+3UL,j) += A(i+3UL,j1) * v1;
1110 for(
size_t i=ipos; i<iend; ++i ) {
1111 C(i,j) += A(i,j1) * v1;
1134 template<
typename MT3
1137 static inline auto selectAddAssignKernel( MT3& C,
const MT4& A,
const MT5& B )
1138 -> EnableIf_t< UseVectorizedKernel_v<MT3,MT4,MT5> >
1140 constexpr
bool remainder( !IsPadded_v<MT3> || !IsPadded_v<MT4> );
1142 for(
size_t j=0UL; j<B.columns(); ++j )
1144 const auto end( B.end(j) );
1145 auto element( B.begin(j) );
1147 const size_t nonzeros( B.nonZeros(j) );
1148 const size_t kpos( nonzeros &
size_t(-4) );
1151 for(
size_t k=0UL; k<kpos; k+=4UL )
1153 const size_t j1( element->index() );
1154 const ET2 v1( element->value() );
1156 const size_t j2( element->index() );
1157 const ET2 v2( element->value() );
1159 const size_t j3( element->index() );
1160 const ET2 v3( element->value() );
1162 const size_t j4( element->index() );
1163 const ET2 v4( element->value() );
1173 const size_t ibegin( ( IsLower_v<MT4> )
1174 ?( ( IsStrictlyLower_v<MT4> )
1178 const size_t iend( ( IsUpper_v<MT4> )
1179 ?( ( IsStrictlyUpper_v<MT4> )
1180 ?(
UPP ?
max(j+1UL,j4) : j4 )
1181 :(
UPP ?
max(j,j4)+1UL : j4+1UL ) )
1182 :(
UPP ? j+1UL : A.rows() ) );
1185 const size_t ipos( remainder ? ( iend &
size_t(-
SIMDSIZE) ) : iend );
1191 C.store( i, j, C.load(i,j) + A.load(i,j1) * xmm1 + A.load(i,j2) * xmm2 + A.load(i,j3) * xmm3 + A.load(i,j4) * xmm4 );
1193 for( ; remainder && i<iend; ++i ) {
1194 C(i,j) += A(i,j1) * v1 + A(i,j2) * v2 + A(i,j3) * v3 + A(i,j4) * v4;
1198 for( ; element!=
end; ++element )
1200 const size_t j1( element->index() );
1201 const ET2 v1( element->value() );
1205 const size_t ibegin( ( IsLower_v<MT4> )
1206 ?( ( IsStrictlyLower_v<MT4> )
1210 const size_t iend( ( IsUpper_v<MT4> )
1211 ?( ( IsStrictlyUpper_v<MT4> )
1212 ?(
UPP ?
max(j+1UL,j1) : j1 )
1213 :(
UPP ?
max(j,j1)+1UL : j1+1UL ) )
1214 :(
UPP ? j+1UL : A.rows() ) );
1217 const size_t ipos( remainder ? ( iend &
size_t(-
SIMDSIZE) ) : iend );
1223 C.store( i, j, C.load(i,j) + A.load(i,j1) * xmm1 );
1225 for( ; remainder && i<iend; ++i ) {
1226 C(i,j) += A(i,j1) * v1;
1251 template<
typename MT
1253 friend inline void subAssign( DenseMatrix<MT,SO>& lhs,
const TDMatTSMatMultExpr& rhs )
1270 TDMatTSMatMultExpr::selectSubAssignKernel( ~lhs, A, B );
1289 template<
typename MT3
1292 static inline auto selectSubAssignKernel( MT3& C,
const MT4& A,
const MT5& B )
1293 -> EnableIf_t< UseDefaultKernel_v<MT3,MT4,MT5> >
1295 const size_t block( IsColumnMajorMatrix_v<MT3> || IsDiagonal_v<MT4> ? A.rows() : 64UL );
1297 for(
size_t ii=0UL; ii<A.rows(); ii+=block )
1299 const size_t itmp(
min( ii+block, A.rows() ) );
1301 for(
size_t j=0UL; j<B.columns(); ++j )
1303 auto element( B.begin(j) );
1304 const auto end( B.end(j) );
1306 for( ; element!=
end; ++element )
1308 const size_t j1( element->index() );
1310 if( IsDiagonal_v<MT4> )
1312 C(j1,j) -= A(j1,j1) * element->value();
1316 const size_t ibegin( ( IsLower_v<MT4> )
1318 ?(
max( j, ii, ( IsStrictlyLower_v<MT4> ? j1+1UL : j1 ) ) )
1319 :(
max( ii, ( IsStrictlyLower_v<MT4> ? j1+1UL : j1 ) ) ) )
1320 :(
LOW ?
max(j,ii) : ii ) );
1321 const size_t iend( ( IsUpper_v<MT4> )
1323 ?(
min( j+1UL, itmp, ( IsStrictlyUpper_v<MT4> ? j1 : j1+1UL ) ) )
1324 :(
min( itmp, ( IsStrictlyUpper_v<MT4> ? j1 : j1+1UL ) ) ) )
1325 :(
UPP ?
min(j+1UL,itmp) : itmp ) );
1327 if( (
LOW ||
UPP || IsTriangular_v<MT4> ) && ( ibegin >= iend ) )
1332 const size_t inum( iend - ibegin );
1333 const size_t ipos( ibegin + ( inum &
size_t(-4) ) );
1336 for(
size_t i=ibegin; i<ipos; i+=4UL ) {
1337 C(i ,j) -= A(i ,j1) * element->value();
1338 C(i+1UL,j) -= A(i+1UL,j1) * element->value();
1339 C(i+2UL,j) -= A(i+2UL,j1) * element->value();
1340 C(i+3UL,j) -= A(i+3UL,j1) * element->value();
1342 for(
size_t i=ipos; i<iend; ++i ) {
1343 C(i,j) -= A(i,j1) * element->value();
1367 template<
typename MT3
1370 static inline auto selectSubAssignKernel( MT3& C,
const MT4& A,
const MT5& B )
1371 -> EnableIf_t< UseOptimizedKernel_v<MT3,MT4,MT5> >
1373 const size_t block( IsColumnMajorMatrix_v<MT3> ? A.rows() : 64UL );
1375 for(
size_t ii=0UL; ii<A.rows(); ii+=block )
1377 const size_t itmp(
min( ii+block, A.rows() ) );
1379 for(
size_t j=0UL; j<B.columns(); ++j )
1381 const auto end( B.end(j) );
1382 auto element( B.begin(j) );
1384 const size_t nonzeros( B.nonZeros(j) );
1385 const size_t kpos( nonzeros &
size_t(-4) );
1388 for(
size_t k=0UL; k<kpos; k+=4UL )
1390 const size_t j1( element->index() );
1391 const ET2 v1( element->value() );
1393 const size_t j2( element->index() );
1394 const ET2 v2( element->value() );
1396 const size_t j3( element->index() );
1397 const ET2 v3( element->value() );
1399 const size_t j4( element->index() );
1400 const ET2 v4( element->value() );
1405 const size_t ibegin( ( IsLower_v<MT4> )
1407 ?(
max( j, ii, ( IsStrictlyLower_v<MT4> ? j1+1UL : j1 ) ) )
1408 :(
max( ii, ( IsStrictlyLower_v<MT4> ? j1+1UL : j1 ) ) ) )
1409 :(
LOW ?
max(j,ii) : ii ) );
1410 const size_t iend( ( IsUpper_v<MT4> )
1412 ?(
min( j+1UL, itmp, ( IsStrictlyUpper_v<MT4> ? j4 : j4+1UL ) ) )
1413 :(
min( itmp, ( IsStrictlyUpper_v<MT4> ? j4 : j4+1UL ) ) ) )
1414 :(
UPP ?
min(j+1UL,itmp) : itmp ) );
1416 if( (
LOW ||
UPP || IsTriangular_v<MT4> ) && ( ibegin >= iend ) )
1421 const size_t inum( iend - ibegin );
1422 const size_t ipos( ibegin + ( inum &
size_t(-4) ) );
1425 for(
size_t i=ibegin; i<ipos; i+=4UL ) {
1426 C(i ,j) -= A(i ,j1) * v1 + A(i ,j2) * v2 + A(i ,j3) * v3 + A(i ,j4) * v4;
1427 C(i+1UL,j) -= A(i+1UL,j1) * v1 + A(i+1UL,j2) * v2 + A(i+1UL,j3) * v3 + A(i+1UL,j4) * v4;
1428 C(i+2UL,j) -= A(i+2UL,j1) * v1 + A(i+2UL,j2) * v2 + A(i+2UL,j3) * v3 + A(i+2UL,j4) * v4;
1429 C(i+3UL,j) -= A(i+3UL,j1) * v1 + A(i+3UL,j2) * v2 + A(i+3UL,j3) * v3 + A(i+3UL,j4) * v4;
1431 for(
size_t i=ipos; i<iend; ++i ) {
1432 C(i,j) -= A(i,j1) * v1 + A(i,j2) * v2 + A(i,j3) * v3 + A(i,j4) * v4;
1436 for( ; element!=
end; ++element )
1438 const size_t j1( element->index() );
1439 const ET2 v1( element->value() );
1441 const size_t ibegin( ( IsLower_v<MT4> )
1443 ?(
max( j, ii, ( IsStrictlyLower_v<MT4> ? j1+1UL : j1 ) ) )
1444 :(
max( ii, ( IsStrictlyLower_v<MT4> ? j1+1UL : j1 ) ) ) )
1445 :(
LOW ?
max(j,ii) : ii ) );
1446 const size_t iend( ( IsUpper_v<MT4> )
1448 ?(
min( j+1UL, itmp, ( IsStrictlyUpper_v<MT4> ? j1 : j1+1UL ) ) )
1449 :(
min( itmp, ( IsStrictlyUpper_v<MT4> ? j1 : j1+1UL ) ) ) )
1450 :(
UPP ?
min(j+1UL,itmp) : itmp ) );
1452 if( (
LOW ||
UPP || IsTriangular_v<MT4> ) && ( ibegin >= iend ) )
1457 const size_t inum( iend - ibegin );
1458 const size_t ipos( ibegin + ( inum &
size_t(-4) ) );
1461 for(
size_t i=ibegin; i<ipos; i+=4UL ) {
1462 C(i ,j) -= A(i ,j1) * v1;
1463 C(i+1UL,j) -= A(i+1UL,j1) * v1;
1464 C(i+2UL,j) -= A(i+2UL,j1) * v1;
1465 C(i+3UL,j) -= A(i+3UL,j1) * v1;
1467 for(
size_t i=ipos; i<iend; ++i ) {
1468 C(i,j) -= A(i,j1) * v1;
1491 template<
typename MT3
1494 static inline auto selectSubAssignKernel( MT3& C,
const MT4& A,
const MT5& B )
1495 -> EnableIf_t< UseVectorizedKernel_v<MT3,MT4,MT5> >
1497 constexpr
bool remainder( !IsPadded_v<MT3> || !IsPadded_v<MT4> );
1499 for(
size_t j=0UL; j<B.columns(); ++j )
1501 const auto end( B.end(j) );
1502 auto element( B.begin(j) );
1504 const size_t nonzeros( B.nonZeros(j) );
1505 const size_t kpos( nonzeros &
size_t(-4) );
1508 for(
size_t k=0UL; k<kpos; k+=4UL )
1510 const size_t j1( element->index() );
1511 const ET2 v1( element->value() );
1513 const size_t j2( element->index() );
1514 const ET2 v2( element->value() );
1516 const size_t j3( element->index() );
1517 const ET2 v3( element->value() );
1519 const size_t j4( element->index() );
1520 const ET2 v4( element->value() );
1530 const size_t ibegin( ( IsLower_v<MT4> )
1531 ?( ( IsStrictlyLower_v<MT4> )
1535 const size_t iend( ( IsUpper_v<MT4> )
1536 ?( ( IsStrictlyUpper_v<MT4> )
1537 ?(
UPP ?
max(j+1UL,j4) : j4 )
1538 :(
UPP ?
max(j,j4)+1UL : j4+1UL ) )
1539 :(
UPP ? j+1UL : A.rows() ) );
1542 const size_t ipos( remainder ? ( iend &
size_t(-
SIMDSIZE) ) : iend );
1548 C.store( i, j, C.load(i,j) - A.load(i,j1) * xmm1 - A.load(i,j2) * xmm2 - A.load(i,j3) * xmm3 - A.load(i,j4) * xmm4 );
1550 for( ; remainder && i<iend; ++i ) {
1551 C(i,j) -= A(i,j1) * v1 + A(i,j2) * v2 + A(i,j3) * v3 + A(i,j4) * v4;
1555 for( ; element!=
end; ++element )
1557 const size_t j1( element->index() );
1558 const ET2 v1( element->value() );
1562 const size_t ibegin( ( IsLower_v<MT4> )
1563 ?( ( IsStrictlyLower_v<MT4> )
1567 const size_t iend( ( IsUpper_v<MT4> )
1568 ?( ( IsStrictlyUpper_v<MT4> )
1569 ?(
UPP ?
max(j+1UL,j1) : j1 )
1570 :(
UPP ?
max(j,j1)+1UL : j1+1UL ) )
1571 :(
UPP ? j+1UL : A.rows() ) );
1574 const size_t ipos( remainder ? ( iend &
size_t(-
SIMDSIZE) ) : iend );
1580 C.store( i, j, C.load(i,j) - A.load(i,j1) * xmm1 );
1582 for( ; remainder && i<iend; ++i ) {
1583 C(i,j) -= A(i,j1) * v1;
1608 template<
typename MT
1610 friend inline void schurAssign( DenseMatrix<MT,SO>& lhs,
const TDMatTSMatMultExpr& rhs )
1622 schurAssign( ~lhs, tmp );
1654 template<
typename MT
1657 -> EnableIf_t< IsEvaluationRequired_v<MT,MT1,MT2> >
1694 template<
typename MT
1697 -> EnableIf_t< IsEvaluationRequired_v<MT,MT1,MT2> >
1701 using TmpType = If_t< SO, ResultType, OppositeType >;
1713 const ForwardFunctor fwd;
1715 const TmpType tmp( rhs );
1736 template<
typename MT
1739 -> EnableIf_t< IsEvaluationRequired_v<MT,MT1,MT2> >
1780 template<
typename MT
1783 -> EnableIf_t< IsEvaluationRequired_v<MT,MT1,MT2> >
1822 template<
typename MT
1888 template<
typename MT1
1890 , DisableIf_t< ( IsIdentity_v<MT2> &&
1891 IsSame_v< ElementType_t<MT1>, ElementType_t<MT2> > ) ||
1892 IsZero_v<MT2> >* =
nullptr >
1893 inline const TDMatTSMatMultExpr<MT1,MT2,false,false,false,false>
1894 tdmattsmatmult(
const DenseMatrix<MT1,true>& lhs,
const SparseMatrix<MT2,true>& rhs )
1900 return TDMatTSMatMultExpr<MT1,MT2,false,false,false,false>( ~lhs, ~rhs );
1920 template<
typename MT1
1922 , EnableIf_t< IsIdentity_v<MT2> &&
1923 IsSame_v< ElementType_t<MT1>, ElementType_t<MT2> > >* =
nullptr >
1925 tdmattsmatmult(
const DenseMatrix<MT1,true>& lhs,
const SparseMatrix<MT2,true>& rhs )
1952 template<
typename MT1
1954 , EnableIf_t< IsZero_v<MT2> >* =
nullptr >
1955 inline decltype(
auto)
1956 tdmattsmatmult( const DenseMatrix<MT1,true>& lhs, const SparseMatrix<MT2,true>& rhs )
1962 using ReturnType =
const MultTrait_t< ResultType_t<MT1>, ResultType_t<MT2> >;
2002 template<
typename MT1
2004 inline decltype(
auto)
2013 return tdmattsmatmult( ~lhs, ~rhs );
2050 template<
typename MT1
2056 inline decltype(
auto)
declsym( const TDMatTSMatMultExpr<MT1,MT2,SF,HF,LF,UF>& dm )
2064 using ReturnType =
const TDMatTSMatMultExpr<MT1,MT2,true,HF,LF,UF>;
2065 return ReturnType( dm.leftOperand(), dm.rightOperand() );
2095 template<
typename MT1
2101 inline decltype(
auto)
declherm( const TDMatTSMatMultExpr<MT1,MT2,SF,HF,LF,UF>& dm )
2109 using ReturnType =
const TDMatTSMatMultExpr<MT1,MT2,SF,true,LF,UF>;
2110 return ReturnType( dm.leftOperand(), dm.rightOperand() );
2140 template<
typename MT1
2146 inline decltype(
auto)
decllow( const TDMatTSMatMultExpr<MT1,MT2,SF,HF,LF,UF>& dm )
2154 using ReturnType =
const TDMatTSMatMultExpr<MT1,MT2,SF,HF,true,UF>;
2155 return ReturnType( dm.leftOperand(), dm.rightOperand() );
2185 template<
typename MT1
2191 inline decltype(
auto)
declupp( const TDMatTSMatMultExpr<MT1,MT2,SF,HF,LF,UF>& dm )
2199 using ReturnType =
const TDMatTSMatMultExpr<MT1,MT2,SF,HF,LF,true>;
2200 return ReturnType( dm.leftOperand(), dm.rightOperand() );
2230 template<
typename MT1
2236 inline decltype(
auto)
decldiag( const TDMatTSMatMultExpr<MT1,MT2,SF,HF,LF,UF>& dm )
2244 using ReturnType =
const TDMatTSMatMultExpr<MT1,MT2,SF,HF,true,true>;
2245 return ReturnType( dm.leftOperand(), dm.rightOperand() );
2261 template<
typename MT1,
typename MT2,
bool SF,
bool HF,
bool LF,
bool UF >
2262 struct Size< TDMatTSMatMultExpr<MT1,MT2,SF,HF,LF,UF>, 0UL >
2263 :
public Size<MT1,0UL>
2266 template<
typename MT1,
typename MT2,
bool SF,
bool HF,
bool LF,
bool UF >
2267 struct Size< TDMatTSMatMultExpr<MT1,MT2,SF,HF,LF,UF>, 1UL >
2268 :
public Size<MT2,1UL>
2284 template<
typename MT1,
typename MT2,
bool SF,
bool HF,
bool LF,
bool UF >
2285 struct IsAligned< TDMatTSMatMultExpr<MT1,MT2,SF,HF,LF,UF> >
2286 :
public IsAligned<MT1>
decltype(auto) subvector(Vector< VT, TF > &, RSAs...)
Creating a view on a specific subvector of the given vector.
Definition: Subvector.h:329
#define BLAZE_THROW_INVALID_ARGUMENT(MESSAGE)
Macro for the emission of a std::invalid_argument exception.This macro encapsulates the default way o...
Definition: Exception.h:235
static constexpr bool evaluateRight
Compilation switch for the composite type of the right-hand side sparse matrix expression.
Definition: TDMatTSMatMultExpr.h:150
Header file for auxiliary alias declarations.
decltype(auto) column(Matrix< MT, SO > &matrix, RCAs... args)
Creating a view on a specific column of the given matrix.
Definition: Column.h:133
Headerfile for the generic min algorithm.
Header file for the blaze::checked and blaze::unchecked instances.
Header file for the decldiag trait.
RightOperand rhs_
Right-hand side sparse matrix of the multiplication expression.
Definition: TDMatTSMatMultExpr.h:463
RightOperand rightOperand() const noexcept
Returns the right-hand side transpose sparse matrix operand.
Definition: TDMatTSMatMultExpr.h:411
decltype(auto) decldiag(const DenseMatrix< MT, SO > &dm)
Declares the given dense matrix expression dm as diagonal.
Definition: DMatDeclDiagExpr.h:975
CompositeType_t< MT2 > CT2
Composite type of the right-hand side sparse matrix expression.
Definition: TDMatTSMatMultExpr.h:140
Header file for basic type definitions.
ResultType_t< MT2 > RT2
Result type of the right-hand side sparse matrix expression.
Definition: TDMatTSMatMultExpr.h:136
typename If< Condition, T1, T2 >::Type If_t
Auxiliary alias declaration for the If class template.The If_t alias declaration provides a convenien...
Definition: If.h:109
ElementType_t< RT2 > ET2
Element type of the right-hand side sparse matrix expression.
Definition: TDMatTSMatMultExpr.h:138
Header file for the declherm trait.
ElementType_t< ResultType > ElementType
Resulting element type.
Definition: TDMatTSMatMultExpr.h:259
Expression object for transpose dense matrix-transpose sparse matrix multiplications.The TDMatTSMatMultExpr class represents the compile time expression for multiplications between a column-major dense matrix and a column-major sparse matrix.
Definition: Forward.h:164
LeftOperand leftOperand() const noexcept
Returns the left-hand side transpose dense matrix operand.
Definition: TDMatTSMatMultExpr.h:401
typename T::ResultType ResultType_t
Alias declaration for nested ResultType type definitions.The ResultType_t alias declaration provides ...
Definition: Aliases.h:390
Header file for the serial shim.
Header file for the IsDiagonal type trait.
Base template for the DeclUppTrait class.
Definition: DeclUppTrait.h:134
#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:61
Header file for the DeclUpp functor.
MT::Iterator begin(Matrix< MT, SO > &matrix, size_t i)
Returns an iterator to the first element of row/column i.
Definition: Matrix.h:372
bool isAliased(const T *alias) const noexcept
Returns whether the expression is aliased with the given address alias.
Definition: TDMatTSMatMultExpr.h:435
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:591
static constexpr bool smpAssignable
Compilation flag for SMP assignments.
Definition: CompressedMatrix.h:3113
static constexpr bool SYM
Flag for symmetric matrices.
Definition: TDMatTSMatMultExpr.h:154
constexpr Unchecked unchecked
Global Unchecked instance.The blaze::unchecked instance is an optional token for the creation of view...
Definition: Check.h:138
Constraint on the data type.
typename SIMDTrait< T >::Type SIMDTrait_t
Auxiliary alias declaration for the SIMDTrait class template.The SIMDTrait_t alias declaration provid...
Definition: SIMDTrait.h:315
ElementType_t< RT1 > ET1
Element type of the left-hand side dense matrix expression.
Definition: TDMatTSMatMultExpr.h:137
bool canAlias(const T *alias) const noexcept
Returns whether the expression can alias with the given address alias.
Definition: TDMatTSMatMultExpr.h:423
Header file for the IsIdentity type trait.
typename If_t< HERM, DeclHermTrait< MultTrait_t< RT1, RT2 > >, If_t< SYM, DeclSymTrait< MultTrait_t< RT1, RT2 > >, If_t< LOW, If_t< UPP, DeclDiagTrait< MultTrait_t< RT1, RT2 > >, DeclLowTrait< MultTrait_t< RT1, RT2 > > >, If_t< UPP, DeclUppTrait< MultTrait_t< RT1, RT2 > >, MultTrait< RT1, RT2 > > > > >::Type ResultType
Result type for expression template evaluations.
Definition: TDMatTSMatMultExpr.h:255
decltype(auto) declupp(const DenseMatrix< MT, SO > &dm)
Declares the given dense matrix expression dm as upper.
Definition: DMatDeclUppExpr.h:1002
Header file for the Computation base class.
Header file for the MatMatMultExpr base class.
Header file for the reset shim.
Constraints on the storage order of matrix types.
Header file for the RequiresEvaluation type trait.
System settings for performance optimizations.
constexpr void UNUSED_PARAMETER(const Args &...)
Suppression of unused parameter warnings.
Definition: Unused.h:81
static constexpr bool LOW
Flag for lower matrices.
Definition: TDMatTSMatMultExpr.h:156
constexpr size_t columns(const Matrix< MT, SO > &matrix) noexcept
Returns the current number of columns of the matrix.
Definition: Matrix.h:514
Base class for dense matrices.The DenseMatrix class is a base class for all dense matrix classes...
Definition: DenseMatrix.h:80
Base class for sparse matrices.The SparseMatrix class is a base class for all sparse matrix classes...
Definition: Forward.h:137
typename T::ElementType ElementType_t
Alias declaration for nested ElementType type definitions.The ElementType_t alias declaration provide...
Definition: Aliases.h:170
Constraint on the data type.
Constraint on the data type.
typename EnableIf< Condition, T >::Type EnableIf_t
Auxiliary type for the EnableIf class template.The EnableIf_t alias declaration provides a convenient...
Definition: EnableIf.h:138
Headerfile for the generic max algorithm.
Header file for the DisableIf class template.
size_t columns() const noexcept
Returns the current number of columns of the matrix.
Definition: TDMatTSMatMultExpr.h:391
Header file for the multiplication trait.
Header file for the IsStrictlyUpper type trait.
size_t rows() const noexcept
Returns the current number of rows of the matrix.
Definition: TDMatTSMatMultExpr.h:381
Namespace of the Blaze C++ math library.
Definition: Blaze.h:58
Header file for the DeclLow functor.
Header file for the If class template.
#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: ColumnMajorMatrix.h:61
#define BLAZE_CONSTRAINT_MUST_BE_ZERO_TYPE(T)
Constraint on the data type.In case the given data type T is not a zero vector or matrix type...
Definition: Zero.h:61
TDMatTSMatMultExpr(const MT1 &lhs, const MT2 &rhs) noexcept
Constructor for the TDMatTSMatMultExpr class.
Definition: TDMatTSMatMultExpr.h:301
Generic wrapper for the decllow() function.
Definition: DeclLow.h:58
decltype(auto) min(const DenseMatrix< MT1, SO1 > &lhs, const DenseMatrix< MT2, SO2 > &rhs)
Computes the componentwise minimum of the dense matrices lhs and rhs.
Definition: DMatDMatMapExpr.h:1147
const ElementType ReturnType
Return type for expression template evaluations.
Definition: TDMatTSMatMultExpr.h:261
Header file for the decllow trait.
static constexpr bool evaluateLeft
Compilation switch for the composite type of the left-hand side dense matrix expression.
Definition: TDMatTSMatMultExpr.h:145
#define BLAZE_THROW_OUT_OF_RANGE(MESSAGE)
Macro for the emission of a std::out_of_range exception.This macro encapsulates the default way of Bl...
Definition: Exception.h:331
Header file for the HasSIMDAdd type trait.
Header file for the DenseMatrix base class.
ResultType_t< MT1 > RT1
Result type of the left-hand side dense matrix expression.
Definition: TDMatTSMatMultExpr.h:135
SIMDTrait_t< ElementType > SIMDType
Resulting SIMD element type.
Definition: TDMatTSMatMultExpr.h:260
Header file for all SIMD functionality.
static constexpr bool UPP
Flag for upper matrices.
Definition: TDMatTSMatMultExpr.h:157
decltype(auto) decllow(const DenseMatrix< MT, SO > &dm)
Declares the given dense matrix expression dm as lower.
Definition: DMatDeclLowExpr.h:1002
Header file for the IsLower type trait.
Header file for the IsAligned type trait.
Generic wrapper for the null function.
Definition: Noop.h:59
Header file for the IsTriangular type trait.
Base template for the DeclSymTrait class.
Definition: DeclSymTrait.h:134
Constraints on the storage order of matrix types.
static constexpr bool simdEnabled
Compilation switch for the expression template evaluation strategy.
Definition: TDMatTSMatMultExpr.h:279
Header file for the exception macros of the math module.
decltype(auto) max(const DenseMatrix< MT1, SO1 > &lhs, const DenseMatrix< MT2, SO2 > &rhs)
Computes the componentwise maximum of the dense matrices lhs and rhs.
Definition: DMatDMatMapExpr.h:1179
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:438
Header file for the DeclDiag functor.
ReturnType operator()(size_t i, size_t j) const
2D-access to the matrix elements.
Definition: TDMatTSMatMultExpr.h:316
static constexpr bool smpAssignable
Compilation switch for the expression template assignment strategy.
Definition: TDMatTSMatMultExpr.h:286
Constraint on the data type.
Header file for all forward declarations for expression class templates.
CompositeType_t< MT1 > CT1
Composite type of the left-hand side dense matrix expression.
Definition: TDMatTSMatMultExpr.h:139
Header file for the EnableIf class template.
Header file for the IsStrictlyLower type trait.
Header file for the IsPadded type trait.
#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:103
typename T::OppositeType OppositeType_t
Alias declaration for nested OppositeType type definitions.The OppositeType_t alias declaration provi...
Definition: Aliases.h:270
Header file for the conjugate shim.
Header file for the declupp trait.
Header file for the IsSIMDCombinable type trait.
#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: RowMajorMatrix.h:61
Header file for the HasSIMDMult type trait.
If_t< IsExpression_v< MT2 >, const MT2, const MT2 &> RightOperand
Composite type of the right-hand side sparse matrix expression.
Definition: TDMatTSMatMultExpr.h:268
typename T::TransposeType TransposeType_t
Alias declaration for nested TransposeType type definitions.The TransposeType_t alias declaration pro...
Definition: Aliases.h:470
Header file for run time assertion macros.
Base template for the DeclHermTrait class.
Definition: DeclHermTrait.h:134
typename T::CompositeType CompositeType_t
Alias declaration for nested CompositeType type definitions.The CompositeType_t alias declaration pro...
Definition: Aliases.h:90
Base template for the MultTrait class.
Definition: MultTrait.h:146
auto smpAddAssign(Matrix< MT1, SO1 > &lhs, const Matrix< MT2, SO2 > &rhs) -> EnableIf_t< IsDenseMatrix_v< MT1 > >
Default implementation of the SMP addition assignment of a matrix to a dense matrix.
Definition: DenseMatrix.h:131
decltype(auto) row(Matrix< MT, SO > &, RRAs...)
Creating a view on a specific row of the given matrix.
Definition: Row.h:133
TransposeType_t< ResultType > TransposeType
Transpose type for expression template evaluations.
Definition: TDMatTSMatMultExpr.h:258
Header file for the IsZero type trait.
SIMD characteristics of data types.The SIMDTrait class template provides the SIMD characteristics of ...
Definition: SIMDTrait.h:295
Header file for the declsym trait.
#define BLAZE_FUNCTION_TRACE
Function trace macro.This macro can be used to reliably trace function calls. In case function tracin...
Definition: FunctionTrace.h:94
decltype(auto) declsym(const DenseMatrix< MT, SO > &dm)
Declares the given dense matrix expression dm as symmetric.
Definition: DMatDeclSymExpr.h:1002
Header file for the isDefault shim.
auto smpAssign(Matrix< MT1, SO1 > &lhs, const Matrix< MT2, SO2 > &rhs) -> EnableIf_t< IsDenseMatrix_v< MT1 > >
Default implementation of the SMP assignment of a matrix to a dense matrix.
Definition: DenseMatrix.h:100
Constraints on the storage order of matrix types.
Generic wrapper for the declherm() function.
Definition: DeclHerm.h:58
decltype(auto) serial(const DenseMatrix< MT, SO > &dm)
Forces the serial evaluation of the given dense matrix expression dm.
Definition: DMatSerialExpr.h:808
Header file for the Noop functor.
#define BLAZE_CONSTRAINT_MUST_NOT_REQUIRE_EVALUATION(T)
Constraint on the data type.In case the given data type T requires an intermediate evaluation within ...
Definition: RequiresEvaluation.h:81
auto smpSchurAssign(Matrix< MT1, SO1 > &lhs, const Matrix< MT2, SO2 > &rhs) -> EnableIf_t< IsDenseMatrix_v< MT1 > >
Default implementation of the SMP Schur product assignment of a matrix to dense matrix.
Definition: DenseMatrix.h:194
constexpr size_t rows(const Matrix< MT, SO > &matrix) noexcept
Returns the current number of rows of the matrix.
Definition: Matrix.h:498
#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:84
Generic wrapper for the declupp() function.
Definition: DeclUpp.h:58
static constexpr size_t SIMDSIZE
The number of elements packed within a single SIMD element.
Definition: TDMatTSMatMultExpr.h:292
const Type & ReturnType
Return type for expression template evaluations.
Definition: CompressedMatrix.h:3081
ReturnType at(size_t i, size_t j) const
Checked access to the matrix elements.
Definition: TDMatTSMatMultExpr.h:365
Base template for the DeclLowTrait class.
Definition: DeclLowTrait.h:134
decltype(auto) declherm(const DenseMatrix< MT, SO > &dm)
Declares the given dense matrix expression dm as Hermitian.
Definition: DMatDeclHermExpr.h:1002
If_t< evaluateLeft, const RT1, CT1 > LT
Type for the assignment of the left-hand side dense matrix operand.
Definition: TDMatTSMatMultExpr.h:271
If_t< IsExpression_v< MT1 >, const MT1, const MT1 &> LeftOperand
Composite type of the left-hand side dense matrix expression.
Definition: TDMatTSMatMultExpr.h:265
Header file for the IsComputation type trait class.
Header file for the IsBuiltin type trait.
auto smpSubAssign(Matrix< MT1, SO1 > &lhs, const Matrix< MT2, SO2 > &rhs) -> EnableIf_t< IsDenseMatrix_v< MT1 > >
Default implementation of the SMP subtraction assignment of a matrix to dense matrix.
Definition: DenseMatrix.h:162
Header file for the IntegralConstant class template.
Generic wrapper for the decldiag() function.
Definition: DeclDiag.h:58
LeftOperand lhs_
Left-hand side dense matrix of the multiplication expression.
Definition: TDMatTSMatMultExpr.h:462
If_t< evaluateRight, const RT2, CT2 > RT
Type for the assignment of the right-hand side sparse matrix operand.
Definition: TDMatTSMatMultExpr.h:274
Header file for the DeclHerm functor.
bool canSMPAssign() const noexcept
Returns whether the expression can be used in SMP assignments.
Definition: TDMatTSMatMultExpr.h:455
bool isDefault(const DiagonalProxy< MT > &proxy)
Returns whether the represented element is in default state.
Definition: DiagonalProxy.h:631
Header file for the IsUpper type trait.
static constexpr bool HERM
Flag for Hermitian matrices.
Definition: TDMatTSMatMultExpr.h:155
decltype(auto) conj(const DenseMatrix< MT, SO > &dm)
Returns a matrix containing the complex conjugate of each single element of dm.
Definition: DMatMapExpr.h:1326
Constraint on the data type.
Generic wrapper for the declsym() function.
Definition: DeclSym.h:58
Base template for the DeclDiagTrait class.
Definition: DeclDiagTrait.h:134
const ResultType CompositeType
Data type for composite expression templates.
Definition: TDMatTSMatMultExpr.h:262
bool isSquare(const Matrix< MT, SO > &matrix) noexcept
Checks if the given matrix is a square matrix.
Definition: Matrix.h:951
Header file for the IsResizable type trait.
OppositeType_t< ResultType > OppositeType
Result type with opposite storage order for expression template evaluations.
Definition: TDMatTSMatMultExpr.h:257
Header file for the Size type trait.
#define BLAZE_CONSTRAINT_MUST_NOT_BE_ZERO_TYPE(T)
Constraint on the data type.In case the given data type T is a zero vector or matrix type...
Definition: Zero.h:81
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 DeclSym functor.
#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:61
Header file for the IsExpression type trait class.
bool isAligned() const noexcept
Returns whether the operands of the expression are properly aligned in memory.
Definition: TDMatTSMatMultExpr.h:445
Header file for the function trace functionality.