Blaze 3.9
SMatEvalExpr.h
Go to the documentation of this file.
1//=================================================================================================
33//=================================================================================================
34
35#ifndef _BLAZE_MATH_EXPRESSIONS_SMATEVALEXPR_H_
36#define _BLAZE_MATH_EXPRESSIONS_SMATEVALEXPR_H_
37
38
39//*************************************************************************************************
40// Includes
41//*************************************************************************************************
42
43#include <blaze/math/Aliases.h>
52#include <blaze/util/Assert.h>
54#include <blaze/util/mpl/If.h>
55#include <blaze/util/Types.h>
56
57
58namespace blaze {
59
60//=================================================================================================
61//
62// CLASS SMATEVALEXPR
63//
64//=================================================================================================
65
66//*************************************************************************************************
73template< typename MT // Type of the sparse matrix
74 , bool SO > // Storage order
76 : public MatEvalExpr< SparseMatrix< SMatEvalExpr<MT,SO>, SO > >
77 , private Computation
78{
79 public:
80 //**Type definitions****************************************************************************
83
86
92
95
97 using Operand = If_t< IsExpression_v<MT>, const MT, const MT& >;
98 //**********************************************************************************************
99
100 //**Compilation flags***************************************************************************
102 static constexpr bool smpAssignable = MT::smpAssignable;
103 //**********************************************************************************************
104
105 //**Constructor*********************************************************************************
110 explicit inline SMatEvalExpr( const MT& sm ) noexcept
111 : sm_( sm ) // Sparse matrix of the evaluation expression
112 {}
113 //**********************************************************************************************
114
115 //**Access operator*****************************************************************************
122 inline ReturnType operator()( size_t i, size_t j ) const {
123 BLAZE_INTERNAL_ASSERT( i < sm_.rows() , "Invalid row access index" );
124 BLAZE_INTERNAL_ASSERT( j < sm_.columns(), "Invalid column access index" );
125 return sm_(i,j);
126 }
127 //**********************************************************************************************
128
129 //**At function*********************************************************************************
137 inline ReturnType at( size_t i, size_t j ) const {
138 if( i >= sm_.rows() ) {
139 BLAZE_THROW_OUT_OF_RANGE( "Invalid row access index" );
140 }
141 if( j >= sm_.columns() ) {
142 BLAZE_THROW_OUT_OF_RANGE( "Invalid column access index" );
143 }
144 return (*this)(i,j);
145 }
146 //**********************************************************************************************
147
148 //**Rows function*******************************************************************************
153 inline size_t rows() const noexcept {
154 return sm_.rows();
155 }
156 //**********************************************************************************************
157
158 //**Columns function****************************************************************************
163 inline size_t columns() const noexcept {
164 return sm_.columns();
165 }
166 //**********************************************************************************************
167
168 //**NonZeros function***************************************************************************
173 inline size_t nonZeros() const {
174 return sm_.nonZeros();
175 }
176 //**********************************************************************************************
177
178 //**NonZeros function***************************************************************************
184 inline size_t nonZeros( size_t i ) const {
185 return sm_.nonZeros(i);
186 }
187 //**********************************************************************************************
188
189 //**Operand access******************************************************************************
194 inline Operand operand() const noexcept {
195 return sm_;
196 }
197 //**********************************************************************************************
198
199 //**********************************************************************************************
205 template< typename T >
206 inline bool canAlias( const T* alias ) const noexcept {
207 return sm_.canAlias( alias );
208 }
209 //**********************************************************************************************
210
211 //**********************************************************************************************
217 template< typename T >
218 inline bool isAliased( const T* alias ) const noexcept {
219 return sm_.isAliased( alias );
220 }
221 //**********************************************************************************************
222
223 //**********************************************************************************************
228 inline bool canSMPAssign() const noexcept {
229 return sm_.canSMPAssign();
230 }
231 //**********************************************************************************************
232
233 private:
234 //**Member variables****************************************************************************
236 //**********************************************************************************************
237
238 //**Assignment to dense matrices****************************************************************
250 template< typename MT2 // Type of the target dense matrix
251 , bool SO2 > // Storage order of the target dense matrix
252 friend inline void assign( DenseMatrix<MT2,SO2>& lhs, const SMatEvalExpr& rhs )
253 {
255
256 BLAZE_INTERNAL_ASSERT( (*lhs).rows() == rhs.rows() , "Invalid number of rows" );
257 BLAZE_INTERNAL_ASSERT( (*lhs).columns() == rhs.columns(), "Invalid number of columns" );
258
259 assign( *lhs, rhs.sm_ );
260 }
262 //**********************************************************************************************
263
264 //**Assignment to sparse matrices***************************************************************
276 template< typename MT2 // Type of the target sparse matrix
277 , bool SO2 > // Storage order of the target sparse matrix
278 friend inline void assign( SparseMatrix<MT2,SO2>& lhs, const SMatEvalExpr& rhs )
279 {
281
282 BLAZE_INTERNAL_ASSERT( (*lhs).rows() == rhs.rows() , "Invalid number of rows" );
283 BLAZE_INTERNAL_ASSERT( (*lhs).columns() == rhs.columns(), "Invalid number of columns" );
284
285 assign( *lhs, rhs.sm_ );
286 }
288 //**********************************************************************************************
289
290 //**Addition assignment to dense matrices*******************************************************
302 template< typename MT2 // Type of the target dense matrix
303 , bool SO2 > // Storage order of the target dense matrix
304 friend inline void addAssign( DenseMatrix<MT2,SO2>& lhs, const SMatEvalExpr& rhs )
305 {
307
308 BLAZE_INTERNAL_ASSERT( (*lhs).rows() == rhs.rows() , "Invalid number of rows" );
309 BLAZE_INTERNAL_ASSERT( (*lhs).columns() == rhs.columns(), "Invalid number of columns" );
310
311 addAssign( *lhs, rhs.sm_ );
312 }
314 //**********************************************************************************************
315
316 //**Addition assignment to sparse matrices******************************************************
328 template< typename MT2 // Type of the target sparse matrix
329 , bool SO2 > // Storage order of the target sparse matrix
330 friend inline void addAssign( SparseMatrix<MT2,SO2>& lhs, const SMatEvalExpr& rhs )
331 {
333
334 BLAZE_INTERNAL_ASSERT( (*lhs).rows() == rhs.rows() , "Invalid number of rows" );
335 BLAZE_INTERNAL_ASSERT( (*lhs).columns() == rhs.columns(), "Invalid number of columns" );
336
337 addAssign( *lhs, rhs.sm_ );
338 }
340 //**********************************************************************************************
341
342 //**Subtraction assignment to dense matrices****************************************************
354 template< typename MT2 // Type of the target dense matrix
355 , bool SO2 > // Storage order of the target dense matrix
356 friend inline void subAssign( DenseMatrix<MT2,SO2>& lhs, const SMatEvalExpr& rhs )
357 {
359
360 BLAZE_INTERNAL_ASSERT( (*lhs).rows() == rhs.rows() , "Invalid number of rows" );
361 BLAZE_INTERNAL_ASSERT( (*lhs).columns() == rhs.columns(), "Invalid number of columns" );
362
363 subAssign( *lhs, rhs.sm_ );
364 }
366 //**********************************************************************************************
367
368 //**Subtraction assignment to sparse matrices***************************************************
380 template< typename MT2 // Type of the target sparse matrix
381 , bool SO2 > // Storage order of the target sparse matrix
382 friend inline void subAssign( SparseMatrix<MT2,SO2>& lhs, const SMatEvalExpr& rhs )
383 {
385
386 BLAZE_INTERNAL_ASSERT( (*lhs).rows() == rhs.rows() , "Invalid number of rows" );
387 BLAZE_INTERNAL_ASSERT( (*lhs).columns() == rhs.columns(), "Invalid number of columns" );
388
389 subAssign( *lhs, rhs.sm_ );
390 }
392 //**********************************************************************************************
393
394 //**Schur product assignment to dense matrices**************************************************
406 template< typename MT2 // Type of the target dense matrix
407 , bool SO2 > // Storage order of the target dense matrix
408 friend inline void schurAssign( DenseMatrix<MT2,SO2>& lhs, const SMatEvalExpr& rhs )
409 {
411
412 BLAZE_INTERNAL_ASSERT( (*lhs).rows() == rhs.rows() , "Invalid number of rows" );
413 BLAZE_INTERNAL_ASSERT( (*lhs).columns() == rhs.columns(), "Invalid number of columns" );
414
415 schurAssign( *lhs, rhs.sm_ );
416 }
418 //**********************************************************************************************
419
420 //**Schur product assignment to sparse matrices*************************************************
432 template< typename MT2 // Type of the target sparse matrix
433 , bool SO2 > // Storage order of the target sparse matrix
434 friend inline void schurAssign( SparseMatrix<MT2,SO2>& lhs, const SMatEvalExpr& rhs )
435 {
437
438 BLAZE_INTERNAL_ASSERT( (*lhs).rows() == rhs.rows() , "Invalid number of rows" );
439 BLAZE_INTERNAL_ASSERT( (*lhs).columns() == rhs.columns(), "Invalid number of columns" );
440
441 schurAssign( *lhs, rhs.sm_ );
442 }
444 //**********************************************************************************************
445
446 //**Multiplication assignment to dense matrices*************************************************
458 template< typename MT2 // Type of the target dense matrix
459 , bool SO2 > // Storage order of the target dense matrix
460 friend inline void multAssign( DenseMatrix<MT2,SO2>& lhs, const SMatEvalExpr& rhs )
461 {
463
464 BLAZE_INTERNAL_ASSERT( (*lhs).rows() == rhs.rows() , "Invalid number of rows" );
465 BLAZE_INTERNAL_ASSERT( (*lhs).columns() == rhs.columns(), "Invalid number of columns" );
466
467 multAssign( *lhs, rhs.sm_ );
468 }
470 //**********************************************************************************************
471
472 //**Multiplication assignment to sparse matrices************************************************
484 template< typename MT2 // Type of the target sparse matrix
485 , bool SO2 > // Storage order of the target sparse matrix
486 friend inline void multAssign( SparseMatrix<MT2,SO2>& lhs, const SMatEvalExpr& rhs )
487 {
489
490 BLAZE_INTERNAL_ASSERT( (*lhs).rows() == rhs.rows() , "Invalid number of rows" );
491 BLAZE_INTERNAL_ASSERT( (*lhs).columns() == rhs.columns(), "Invalid number of columns" );
492
493 multAssign( *lhs, rhs.sm_ );
494 }
496 //**********************************************************************************************
497
498 //**SMP assignment to dense matrices************************************************************
510 template< typename MT2 // Type of the target dense matrix
511 , bool SO2 > // Storage order of the target dense matrix
512 friend inline void smpAssign( DenseMatrix<MT2,SO2>& lhs, const SMatEvalExpr& rhs )
513 {
515
516 BLAZE_INTERNAL_ASSERT( (*lhs).rows() == rhs.rows() , "Invalid number of rows" );
517 BLAZE_INTERNAL_ASSERT( (*lhs).columns() == rhs.columns(), "Invalid number of columns" );
518
519 smpAssign( *lhs, rhs.sm_ );
520 }
522 //**********************************************************************************************
523
524 //**SMP assignment to sparse matrices***********************************************************
536 template< typename MT2 // Type of the target sparse matrix
537 , bool SO2 > // Storage order of the target sparse matrix
538 friend inline void smpAssign( SparseMatrix<MT2,SO2>& lhs, const SMatEvalExpr& rhs )
539 {
541
542 BLAZE_INTERNAL_ASSERT( (*lhs).rows() == rhs.rows() , "Invalid number of rows" );
543 BLAZE_INTERNAL_ASSERT( (*lhs).columns() == rhs.columns(), "Invalid number of columns" );
544
545 smpAssign( *lhs, rhs.sm_ );
546 }
548 //**********************************************************************************************
549
550 //**SMP addition assignment to dense matrices***************************************************
562 template< typename MT2 // Type of the target dense matrix
563 , bool SO2 > // Storage order of the target dense matrix
564 friend inline void smpAddAssign( DenseMatrix<MT2,SO2>& lhs, const SMatEvalExpr& rhs )
565 {
567
568 BLAZE_INTERNAL_ASSERT( (*lhs).rows() == rhs.rows() , "Invalid number of rows" );
569 BLAZE_INTERNAL_ASSERT( (*lhs).columns() == rhs.columns(), "Invalid number of columns" );
570
571 smpAddAssign( *lhs, rhs.sm_ );
572 }
574 //**********************************************************************************************
575
576 //**SMP addition assignment to sparse matrices**************************************************
588 template< typename MT2 // Type of the target sparse matrix
589 , bool SO2 > // Storage order of the target sparse matrix
590 friend inline void smpAddAssign( SparseMatrix<MT2,SO2>& lhs, const SMatEvalExpr& rhs )
591 {
593
594 BLAZE_INTERNAL_ASSERT( (*lhs).rows() == rhs.rows() , "Invalid number of rows" );
595 BLAZE_INTERNAL_ASSERT( (*lhs).columns() == rhs.columns(), "Invalid number of columns" );
596
597 smpAddAssign( *lhs, rhs.sm_ );
598 }
600 //**********************************************************************************************
601
602 //**SMP subtraction assignment to dense matrices************************************************
614 template< typename MT2 // Type of the target dense matrix
615 , bool SO2 > // Storage order of the target dense matrix
616 friend inline void smpSubAssign( DenseMatrix<MT2,SO2>& lhs, const SMatEvalExpr& rhs )
617 {
619
620 BLAZE_INTERNAL_ASSERT( (*lhs).rows() == rhs.rows() , "Invalid number of rows" );
621 BLAZE_INTERNAL_ASSERT( (*lhs).columns() == rhs.columns(), "Invalid number of columns" );
622
623 smpSubAssign( *lhs, rhs.sm_ );
624 }
626 //**********************************************************************************************
627
628 //**SMP subtraction assignment to sparse matrices***********************************************
640 template< typename MT2 // Type of the target sparse matrix
641 , bool SO2 > // Storage order of the target sparse matrix
642 friend inline void smpSubAssign( SparseMatrix<MT2,SO2>& lhs, const SMatEvalExpr& rhs )
643 {
645
646 BLAZE_INTERNAL_ASSERT( (*lhs).rows() == rhs.rows() , "Invalid number of rows" );
647 BLAZE_INTERNAL_ASSERT( (*lhs).columns() == rhs.columns(), "Invalid number of columns" );
648
649 smpSubAssign( *lhs, rhs.sm_ );
650 }
652 //**********************************************************************************************
653
654 //**SMP Schur product assignment to dense matrices**********************************************
667 template< typename MT2 // Type of the target dense matrix
668 , bool SO2 > // Storage order of the target dense matrix
669 friend inline void smpSchurAssign( DenseMatrix<MT2,SO2>& lhs, const SMatEvalExpr& rhs )
670 {
672
673 BLAZE_INTERNAL_ASSERT( (*lhs).rows() == rhs.rows() , "Invalid number of rows" );
674 BLAZE_INTERNAL_ASSERT( (*lhs).columns() == rhs.columns(), "Invalid number of columns" );
675
676 smpSchurAssign( *lhs, rhs.sm_ );
677 }
679 //**********************************************************************************************
680
681 //**SMP Schur product assignment to sparse matrices*********************************************
694 template< typename MT2 // Type of the target sparse matrix
695 , bool SO2 > // Storage order of the target sparse matrix
696 friend inline void smpSchurAssign( SparseMatrix<MT2,SO2>& lhs, const SMatEvalExpr& rhs )
697 {
699
700 BLAZE_INTERNAL_ASSERT( (*lhs).rows() == rhs.rows() , "Invalid number of rows" );
701 BLAZE_INTERNAL_ASSERT( (*lhs).columns() == rhs.columns(), "Invalid number of columns" );
702
703 smpSchurAssign( *lhs, rhs.sm_ );
704 }
706 //**********************************************************************************************
707
708 //**SMP multiplication assignment to dense matrices*********************************************
721 template< typename MT2 // Type of the target dense matrix
722 , bool SO2 > // Storage order of the target dense matrix
723 friend inline void smpMultAssign( DenseMatrix<MT2,SO2>& lhs, const SMatEvalExpr& rhs )
724 {
726
727 BLAZE_INTERNAL_ASSERT( (*lhs).rows() == rhs.rows() , "Invalid number of rows" );
728 BLAZE_INTERNAL_ASSERT( (*lhs).columns() == rhs.columns(), "Invalid number of columns" );
729
730 smpMultAssign( *lhs, rhs.sm_ );
731 }
733 //**********************************************************************************************
734
735 //**SMP multiplication assignment to sparse matrices********************************************
748 template< typename MT2 // Type of the target sparse matrix
749 , bool SO2 > // Storage order of the target sparse matrix
750 friend inline void smpMultAssign( SparseMatrix<MT2,SO2>& lhs, const SMatEvalExpr& rhs )
751 {
753
754 BLAZE_INTERNAL_ASSERT( (*lhs).rows() == rhs.rows() , "Invalid number of rows" );
755 BLAZE_INTERNAL_ASSERT( (*lhs).columns() == rhs.columns(), "Invalid number of columns" );
756
757 smpMultAssign( *lhs, rhs.sm_ );
758 }
760 //**********************************************************************************************
761
762 //**Compile time checks*************************************************************************
767 //**********************************************************************************************
768};
769//*************************************************************************************************
770
771
772
773
774//=================================================================================================
775//
776// GLOBAL FUNCTIONS
777//
778//=================================================================================================
779
780//*************************************************************************************************
797template< typename MT // Type of the sparse matrix
798 , bool SO > // Storage order
799inline decltype(auto) eval( const SparseMatrix<MT,SO>& sm )
800{
802
803 using ReturnType = const SMatEvalExpr<MT,SO>;
804 return ReturnType( *sm );
805}
806//*************************************************************************************************
807
808} // namespace blaze
809
810#endif
Header file for auxiliary alias declarations.
typename T::ReturnType ReturnType_t
Alias declaration for nested ReturnType type definitions.
Definition: Aliases.h:470
typename T::ResultType ResultType_t
Alias declaration for nested ResultType type definitions.
Definition: Aliases.h:450
typename T::ElementType ElementType_t
Alias declaration for nested ElementType type definitions.
Definition: Aliases.h:190
typename T::OppositeType OppositeType_t
Alias declaration for nested OppositeType type definitions.
Definition: Aliases.h:310
typename T::TransposeType TransposeType_t
Alias declaration for nested TransposeType type definitions.
Definition: Aliases.h:550
Header file for run time assertion macros.
Header file for the function trace functionality.
Header file for the If class template.
Header file for the IsExpression type trait class.
Base class for dense matrices.
Definition: DenseMatrix.h:82
Expression object for the forced evaluation of sparse matrices.
Definition: SMatEvalExpr.h:78
Operand sm_
Sparse matrix of the evaluation expression.
Definition: SMatEvalExpr.h:235
SMatEvalExpr(const MT &sm) noexcept
Constructor for the SMatEvalExpr class.
Definition: SMatEvalExpr.h:110
If_t< IsExpression_v< MT >, const MT, const MT & > Operand
Composite data type of the sparse matrix expression.
Definition: SMatEvalExpr.h:97
size_t rows() const noexcept
Returns the current number of rows of the matrix.
Definition: SMatEvalExpr.h:153
size_t nonZeros() const
Returns the number of non-zero elements in the sparse matrix.
Definition: SMatEvalExpr.h:173
OppositeType_t< MT > OppositeType
Result type with opposite storage order for expression template evaluations.
Definition: SMatEvalExpr.h:88
ReturnType operator()(size_t i, size_t j) const
2D-access to the matrix elements.
Definition: SMatEvalExpr.h:122
bool canAlias(const T *alias) const noexcept
Returns whether the expression can alias with the given address alias.
Definition: SMatEvalExpr.h:206
size_t nonZeros(size_t i) const
Returns the number of non-zero elements in the specified row.
Definition: SMatEvalExpr.h:184
ElementType_t< MT > ElementType
Resulting element type.
Definition: SMatEvalExpr.h:90
static constexpr bool smpAssignable
Compilation switch for the expression template assignment strategy.
Definition: SMatEvalExpr.h:102
TransposeType_t< MT > TransposeType
Transpose type for expression template evaluations.
Definition: SMatEvalExpr.h:89
ResultType_t< MT > ResultType
Result type for expression template evaluations.
Definition: SMatEvalExpr.h:87
ReturnType_t< MT > ReturnType
Return type for expression template evaluations.
Definition: SMatEvalExpr.h:91
ReturnType at(size_t i, size_t j) const
Checked access to the matrix elements.
Definition: SMatEvalExpr.h:137
Operand operand() const noexcept
Returns the sparse matrix operand.
Definition: SMatEvalExpr.h:194
size_t columns() const noexcept
Returns the current number of columns of the matrix.
Definition: SMatEvalExpr.h:163
bool canSMPAssign() const noexcept
Returns whether the expression can be used in SMP assignments.
Definition: SMatEvalExpr.h:228
bool isAliased(const T *alias) const noexcept
Returns whether the expression is aliased with the given address alias.
Definition: SMatEvalExpr.h:218
const ResultType CompositeType
Data type for composite expression templates.
Definition: SMatEvalExpr.h:94
Base class for sparse matrices.
Definition: SparseMatrix.h:77
Constraint on the data type.
Header file for the Computation base class.
Header file for the MatEvalExpr base class.
Header file for the SparseMatrix base class.
decltype(auto) eval(const DenseMatrix< MT, SO > &dm)
Forces the evaluation of the given dense matrix expression dm.
Definition: DMatEvalExpr.h:790
#define BLAZE_CONSTRAINT_MUST_BE_SPARSE_MATRIX_TYPE(T)
Constraint on the data type.
Definition: SparseMatrix.h:61
#define BLAZE_CONSTRAINT_MUST_BE_MATRIX_WITH_STORAGE_ORDER(T, SO)
Constraint on the data type.
Definition: StorageOrder.h:63
#define BLAZE_INTERNAL_ASSERT(expr, msg)
Run time assertion macro for internal checks.
Definition: Assert.h:101
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
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
auto smpMultAssign(Vector< VT1, TF1 > &lhs, const Vector< VT2, TF2 > &rhs) -> EnableIf_t< IsDenseVector_v< VT1 > >
Default implementation of the SMP multiplication assignment of a vector to a dense vector.
Definition: DenseVector.h:192
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
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
typename If< Condition >::template Type< T1, T2 > If_t
Auxiliary alias template for the If class template.
Definition: If.h:108
#define BLAZE_THROW_OUT_OF_RANGE(MESSAGE)
Macro for the emission of a std::out_of_range exception.
Definition: Exception.h:331
#define BLAZE_FUNCTION_TRACE
Function trace macro.
Definition: FunctionTrace.h:94
Header file for the exception macros of the math module.
Constraints on the storage order of matrix types.
Header file for all forward declarations for expression class templates.
Base class for all compute expression templates.
Definition: Computation.h:68
Base class for all matrix evaluation expression templates.
Definition: MatEvalExpr.h:69
Header file for basic type definitions.