DynamicMatrix.h
Go to the documentation of this file.
1 //=================================================================================================
33 //=================================================================================================
34 
35 #ifndef _BLAZE_MATH_DENSE_DYNAMICMATRIX_H_
36 #define _BLAZE_MATH_DENSE_DYNAMICMATRIX_H_
37 
38 
39 //*************************************************************************************************
40 // Includes
41 //*************************************************************************************************
42 
43 #include <algorithm>
44 #include <utility>
45 #include <blaze/math/Aliases.h>
50 #include <blaze/math/Exception.h>
53 #include <blaze/math/Forward.h>
55 #include <blaze/math/shims/Clear.h>
59 #include <blaze/math/shims/Reset.h>
60 #include <blaze/math/SIMD.h>
100 #include <blaze/system/Blocking.h>
101 #include <blaze/system/CacheSize.h>
102 #include <blaze/system/Inline.h>
104 #include <blaze/system/Restrict.h>
106 #include <blaze/system/Thresholds.h>
112 #include <blaze/util/Assert.h>
118 #include <blaze/util/DisableIf.h>
119 #include <blaze/util/EnableIf.h>
121 #include <blaze/util/Memory.h>
122 #include <blaze/util/TrueType.h>
123 #include <blaze/util/Types.h>
128 #include <blaze/util/Unused.h>
129 
130 
131 namespace blaze {
132 
133 //=================================================================================================
134 //
135 // CLASS DEFINITION
136 //
137 //=================================================================================================
138 
139 //*************************************************************************************************
218 template< typename Type // Data type of the matrix
219  , bool SO = defaultStorageOrder > // Storage order
221  : public DenseMatrix< DynamicMatrix<Type,SO>, SO >
222 {
223  public:
224  //**Type definitions****************************************************************************
227  using ResultType = This;
230  using ElementType = Type;
232  using ReturnType = const Type&;
233  using CompositeType = const This&;
234 
235  using Reference = Type&;
236  using ConstReference = const Type&;
237  using Pointer = Type*;
238  using ConstPointer = const Type*;
239 
242  //**********************************************************************************************
243 
244  //**Rebind struct definition********************************************************************
247  template< typename NewType > // Data type of the other matrix
248  struct Rebind {
250  };
251  //**********************************************************************************************
252 
253  //**Resize struct definition********************************************************************
256  template< size_t NewM // Number of rows of the other matrix
257  , size_t NewN > // Number of columns of the other matrix
258  struct Resize {
260  };
261  //**********************************************************************************************
262 
263  //**Compilation flags***************************************************************************
265 
269  static constexpr bool simdEnabled = IsVectorizable_v<Type>;
270 
272 
275  static constexpr bool smpAssignable = !IsSMPAssignable_v<Type>;
276  //**********************************************************************************************
277 
278  //**Constructors********************************************************************************
281  explicit inline DynamicMatrix() noexcept;
282  explicit inline DynamicMatrix( size_t m, size_t n );
283  explicit inline DynamicMatrix( size_t m, size_t n, const Type& init );
284  explicit inline DynamicMatrix( initializer_list< initializer_list<Type> > list );
285 
286  template< typename Other >
287  explicit inline DynamicMatrix( size_t m, size_t n, const Other* array );
288 
289  template< typename Other, size_t Rows, size_t Cols >
290  explicit inline DynamicMatrix( const Other (&array)[Rows][Cols] );
291 
292  inline DynamicMatrix( const DynamicMatrix& m );
293  inline DynamicMatrix( DynamicMatrix&& m ) noexcept;
294  template< typename MT, bool SO2 > inline DynamicMatrix( const Matrix<MT,SO2>& m );
296  //**********************************************************************************************
297 
298  //**Destructor**********************************************************************************
301  inline ~DynamicMatrix();
303  //**********************************************************************************************
304 
305  //**Data access functions***********************************************************************
308  inline Reference operator()( size_t i, size_t j ) noexcept;
309  inline ConstReference operator()( size_t i, size_t j ) const noexcept;
310  inline Reference at( size_t i, size_t j );
311  inline ConstReference at( size_t i, size_t j ) const;
312  inline Pointer data () noexcept;
313  inline ConstPointer data () const noexcept;
314  inline Pointer data ( size_t i ) noexcept;
315  inline ConstPointer data ( size_t i ) const noexcept;
316  inline Iterator begin ( size_t i ) noexcept;
317  inline ConstIterator begin ( size_t i ) const noexcept;
318  inline ConstIterator cbegin( size_t i ) const noexcept;
319  inline Iterator end ( size_t i ) noexcept;
320  inline ConstIterator end ( size_t i ) const noexcept;
321  inline ConstIterator cend ( size_t i ) const noexcept;
323  //**********************************************************************************************
324 
325  //**Assignment operators************************************************************************
328  inline DynamicMatrix& operator=( const Type& rhs );
329  inline DynamicMatrix& operator=( initializer_list< initializer_list<Type> > list );
330 
331  template< typename Other, size_t Rows, size_t Cols >
332  inline DynamicMatrix& operator=( const Other (&array)[Rows][Cols] );
333 
334  inline DynamicMatrix& operator=( const DynamicMatrix& rhs );
335  inline DynamicMatrix& operator=( DynamicMatrix&& rhs ) noexcept;
336 
337  template< typename MT, bool SO2 > inline DynamicMatrix& operator= ( const Matrix<MT,SO2>& rhs );
338  template< typename MT, bool SO2 > inline DynamicMatrix& operator+=( const Matrix<MT,SO2>& rhs );
339  template< typename MT, bool SO2 > inline DynamicMatrix& operator-=( const Matrix<MT,SO2>& rhs );
340  template< typename MT, bool SO2 > inline DynamicMatrix& operator%=( const Matrix<MT,SO2>& rhs );
342  //**********************************************************************************************
343 
344  //**Utility functions***************************************************************************
347  inline size_t rows() const noexcept;
348  inline size_t columns() const noexcept;
349  inline size_t spacing() const noexcept;
350  inline size_t capacity() const noexcept;
351  inline size_t capacity( size_t i ) const noexcept;
352  inline size_t nonZeros() const;
353  inline size_t nonZeros( size_t i ) const;
354  inline void reset();
355  inline void reset( size_t i );
356  inline void clear();
357  void resize ( size_t m, size_t n, bool preserve=true );
358  inline void extend ( size_t m, size_t n, bool preserve=true );
359  inline void reserve( size_t elements );
360  inline void shrinkToFit();
361  inline void swap( DynamicMatrix& m ) noexcept;
363  //**********************************************************************************************
364 
365  //**Numeric functions***************************************************************************
368  inline DynamicMatrix& transpose();
369  inline DynamicMatrix& ctranspose();
370 
371  template< typename Other > inline DynamicMatrix& scale( const Other& scalar );
373  //**********************************************************************************************
374 
375  private:
376  //**********************************************************************************************
378  template< typename MT >
380  static constexpr bool VectorizedAssign_v =
381  ( useOptimizedKernels &&
382  simdEnabled && MT::simdEnabled &&
383  IsSIMDCombinable_v< Type, ElementType_t<MT> > );
385  //**********************************************************************************************
386 
387  //**********************************************************************************************
389  template< typename MT >
391  static constexpr bool VectorizedAddAssign_v =
392  ( useOptimizedKernels &&
393  simdEnabled && MT::simdEnabled &&
394  IsSIMDCombinable_v< Type, ElementType_t<MT> > &&
395  HasSIMDAdd_v< Type, ElementType_t<MT> > &&
396  !IsDiagonal_v<MT> );
398  //**********************************************************************************************
399 
400  //**********************************************************************************************
402  template< typename MT >
404  static constexpr bool VectorizedSubAssign_v =
405  ( useOptimizedKernels &&
406  simdEnabled && MT::simdEnabled &&
407  IsSIMDCombinable_v< Type, ElementType_t<MT> > &&
408  HasSIMDSub_v< Type, ElementType_t<MT> > &&
409  !IsDiagonal_v<MT> );
411  //**********************************************************************************************
412 
413  //**********************************************************************************************
415  template< typename MT >
417  static constexpr bool VectorizedSchurAssign_v =
418  ( useOptimizedKernels &&
419  simdEnabled && MT::simdEnabled &&
420  IsSIMDCombinable_v< Type, ElementType_t<MT> > &&
421  HasSIMDMult_v< Type, ElementType_t<MT> > );
423  //**********************************************************************************************
424 
425  //**********************************************************************************************
427  static constexpr size_t SIMDSIZE = SIMDTrait<ElementType>::size;
428  //**********************************************************************************************
429 
430  public:
431  //**Debugging functions*************************************************************************
434  inline bool isIntact() const noexcept;
436  //**********************************************************************************************
437 
438  //**Expression template evaluation functions****************************************************
441  template< typename Other > inline bool canAlias ( const Other* alias ) const noexcept;
442  template< typename Other > inline bool isAliased( const Other* alias ) const noexcept;
443 
444  inline bool isAligned () const noexcept;
445  inline bool canSMPAssign() const noexcept;
446 
447  BLAZE_ALWAYS_INLINE SIMDType load ( size_t i, size_t j ) const noexcept;
448  BLAZE_ALWAYS_INLINE SIMDType loada( size_t i, size_t j ) const noexcept;
449  BLAZE_ALWAYS_INLINE SIMDType loadu( size_t i, size_t j ) const noexcept;
450 
451  BLAZE_ALWAYS_INLINE void store ( size_t i, size_t j, const SIMDType& value ) noexcept;
452  BLAZE_ALWAYS_INLINE void storea( size_t i, size_t j, const SIMDType& value ) noexcept;
453  BLAZE_ALWAYS_INLINE void storeu( size_t i, size_t j, const SIMDType& value ) noexcept;
454  BLAZE_ALWAYS_INLINE void stream( size_t i, size_t j, const SIMDType& value ) noexcept;
455 
456  template< typename MT >
457  inline auto assign( const DenseMatrix<MT,SO>& rhs ) -> DisableIf_t< VectorizedAssign_v<MT> >;
458 
459  template< typename MT >
460  inline auto assign( const DenseMatrix<MT,SO>& rhs ) -> EnableIf_t< VectorizedAssign_v<MT> >;
461 
462  template< typename MT > inline void assign( const DenseMatrix<MT,!SO>& rhs );
463  template< typename MT > inline void assign( const SparseMatrix<MT,SO>& rhs );
464  template< typename MT > inline void assign( const SparseMatrix<MT,!SO>& rhs );
465 
466  template< typename MT >
467  inline auto addAssign( const DenseMatrix<MT,SO>& rhs ) -> DisableIf_t< VectorizedAddAssign_v<MT> >;
468 
469  template< typename MT >
470  inline auto addAssign( const DenseMatrix<MT,SO>& rhs ) -> EnableIf_t< VectorizedAddAssign_v<MT> >;
471 
472  template< typename MT > inline void addAssign( const DenseMatrix<MT,!SO>& rhs );
473  template< typename MT > inline void addAssign( const SparseMatrix<MT,SO>& rhs );
474  template< typename MT > inline void addAssign( const SparseMatrix<MT,!SO>& rhs );
475 
476  template< typename MT >
477  inline auto subAssign( const DenseMatrix<MT,SO>& rhs ) -> DisableIf_t< VectorizedSubAssign_v<MT> >;
478 
479  template< typename MT >
480  inline auto subAssign( const DenseMatrix<MT,SO>& rhs ) -> EnableIf_t< VectorizedSubAssign_v<MT> >;
481 
482  template< typename MT > inline void subAssign( const DenseMatrix<MT,!SO>& rhs );
483  template< typename MT > inline void subAssign( const SparseMatrix<MT,SO>& rhs );
484  template< typename MT > inline void subAssign( const SparseMatrix<MT,!SO>& rhs );
485 
486  template< typename MT >
487  inline auto schurAssign( const DenseMatrix<MT,SO>& rhs ) -> DisableIf_t< VectorizedSchurAssign_v<MT> >;
488 
489  template< typename MT >
490  inline auto schurAssign( const DenseMatrix<MT,SO>& rhs ) -> EnableIf_t< VectorizedSchurAssign_v<MT> >;
491 
492  template< typename MT > inline void schurAssign( const DenseMatrix<MT,!SO>& rhs );
493  template< typename MT > inline void schurAssign( const SparseMatrix<MT,SO>& rhs );
494  template< typename MT > inline void schurAssign( const SparseMatrix<MT,!SO>& rhs );
496  //**********************************************************************************************
497 
498  private:
499  //**Utility functions***************************************************************************
502  inline size_t addPadding( size_t value ) const noexcept;
504  //**********************************************************************************************
505 
506  //**Member variables****************************************************************************
509  size_t m_;
510  size_t n_;
511  size_t nn_;
512  size_t capacity_;
514 
524  //**********************************************************************************************
525 
526  //**Compile time checks*************************************************************************
533  //**********************************************************************************************
534 };
535 //*************************************************************************************************
536 
537 
538 
539 
540 //=================================================================================================
541 //
542 // CONSTRUCTORS
543 //
544 //=================================================================================================
545 
546 //*************************************************************************************************
549 template< typename Type // Data type of the matrix
550  , bool SO > // Storage order
551 inline DynamicMatrix<Type,SO>::DynamicMatrix() noexcept
552  : m_ ( 0UL ) // The current number of rows of the matrix
553  , n_ ( 0UL ) // The current number of columns of the matrix
554  , nn_ ( 0UL ) // The alignment adjusted number of columns
555  , capacity_( 0UL ) // The maximum capacity of the matrix
556  , v_ ( nullptr ) // The matrix elements
557 {}
558 //*************************************************************************************************
559 
560 
561 //*************************************************************************************************
570 template< typename Type // Data type of the matrix
571  , bool SO > // Storage order
572 inline DynamicMatrix<Type,SO>::DynamicMatrix( size_t m, size_t n )
573  : m_ ( m ) // The current number of rows of the matrix
574  , n_ ( n ) // The current number of columns of the matrix
575  , nn_ ( addPadding( n ) ) // The alignment adjusted number of columns
576  , capacity_( m_*nn_ ) // The maximum capacity of the matrix
577  , v_ ( allocate<Type>( capacity_ ) ) // The matrix elements
578 {
579  if( IsVectorizable_v<Type> ) {
580  for( size_t i=0UL; i<m_; ++i ) {
581  for( size_t j=n_; j<nn_; ++j ) {
582  v_[i*nn_+j] = Type();
583  }
584  }
585  }
586 
587  BLAZE_INTERNAL_ASSERT( isIntact(), "Invariant violation detected" );
588 }
589 //*************************************************************************************************
590 
591 
592 //*************************************************************************************************
601 template< typename Type // Data type of the matrix
602  , bool SO > // Storage order
603 inline DynamicMatrix<Type,SO>::DynamicMatrix( size_t m, size_t n, const Type& init )
604  : DynamicMatrix( m, n )
605 {
606  for( size_t i=0UL; i<m; ++i ) {
607  for( size_t j=0UL; j<n_; ++j ) {
608  v_[i*nn_+j] = init;
609  }
610  }
611 
612  BLAZE_INTERNAL_ASSERT( isIntact(), "Invariant violation detected" );
613 }
614 //*************************************************************************************************
615 
616 
617 //*************************************************************************************************
637 template< typename Type // Data type of the matrix
638  , bool SO > // Storage order
640  : DynamicMatrix( list.size(), determineColumns( list ) )
641 {
642  size_t i( 0UL );
643 
644  for( const auto& rowList : list ) {
645  std::fill( std::copy( rowList.begin(), rowList.end(), begin(i) ), end(i), Type() );
646  ++i;
647  }
648 
649  BLAZE_INTERNAL_ASSERT( isIntact(), "Invariant violation detected" );
650 }
651 //*************************************************************************************************
652 
653 
654 //*************************************************************************************************
677 template< typename Type // Data type of the matrix
678  , bool SO > // Storage order
679 template< typename Other > // Data type of the initialization array
680 inline DynamicMatrix<Type,SO>::DynamicMatrix( size_t m, size_t n, const Other* array )
681  : DynamicMatrix( m, n )
682 {
683  for( size_t i=0UL; i<m; ++i ) {
684  for( size_t j=0UL; j<n; ++j ) {
685  v_[i*nn_+j] = array[i*n+j];
686  }
687  }
688 
689  BLAZE_INTERNAL_ASSERT( isIntact(), "Invariant violation detected" );
690 }
691 //*************************************************************************************************
692 
693 
694 //*************************************************************************************************
715 template< typename Type // Data type of the matrix
716  , bool SO > // Storage order
717 template< typename Other // Data type of the initialization array
718  , size_t Rows // Number of rows of the initialization array
719  , size_t Cols > // Number of columns of the initialization array
720 inline DynamicMatrix<Type,SO>::DynamicMatrix( const Other (&array)[Rows][Cols] )
721  : DynamicMatrix( Rows, Cols )
722 {
723  for( size_t i=0UL; i<Rows; ++i ) {
724  for( size_t j=0UL; j<Cols; ++j ) {
725  v_[i*nn_+j] = array[i][j];
726  }
727  }
728 
729  BLAZE_INTERNAL_ASSERT( isIntact(), "Invariant violation detected" );
730 }
731 //*************************************************************************************************
732 
733 
734 //*************************************************************************************************
742 template< typename Type // Data type of the matrix
743  , bool SO > // Storage order
745  : DynamicMatrix( m.m_, m.n_ )
746 {
747  BLAZE_INTERNAL_ASSERT( capacity_ <= m.capacity_, "Invalid capacity estimation" );
748 
749  smpAssign( *this, m );
750 
751  BLAZE_INTERNAL_ASSERT( isIntact(), "Invariant violation detected" );
752 }
753 //*************************************************************************************************
754 
755 
756 //*************************************************************************************************
761 template< typename Type // Data type of the matrix
762  , bool SO > // Storage order
764  : m_ ( m.m_ ) // The current number of rows of the matrix
765  , n_ ( m.n_ ) // The current number of columns of the matrix
766  , nn_ ( m.nn_ ) // The alignment adjusted number of columns
767  , capacity_( m.capacity_ ) // The maximum capacity of the matrix
768  , v_ ( m.v_ ) // The matrix elements
769 {
770  m.m_ = 0UL;
771  m.n_ = 0UL;
772  m.nn_ = 0UL;
773  m.capacity_ = 0UL;
774  m.v_ = nullptr;
775 }
776 //*************************************************************************************************
777 
778 
779 //*************************************************************************************************
784 template< typename Type // Data type of the matrix
785  , bool SO > // Storage order
786 template< typename MT // Type of the foreign matrix
787  , bool SO2 > // Storage order of the foreign matrix
789  : DynamicMatrix( (~m).rows(), (~m).columns() )
790 {
791  if( IsSparseMatrix_v<MT> ) {
792  reset();
793  }
794 
795  smpAssign( *this, ~m );
796 
797  BLAZE_INTERNAL_ASSERT( isIntact(), "Invariant violation detected" );
798 }
799 //*************************************************************************************************
800 
801 
802 
803 
804 //=================================================================================================
805 //
806 // DESTRUCTOR
807 //
808 //=================================================================================================
809 
810 //*************************************************************************************************
813 template< typename Type // Data type of the matrix
814  , bool SO > // Storage order
816 {
817  deallocate( v_ );
818 }
819 //*************************************************************************************************
820 
821 
822 
823 
824 //=================================================================================================
825 //
826 // DATA ACCESS FUNCTIONS
827 //
828 //=================================================================================================
829 
830 //*************************************************************************************************
840 template< typename Type // Data type of the matrix
841  , bool SO > // Storage order
842 inline typename DynamicMatrix<Type,SO>::Reference
843  DynamicMatrix<Type,SO>::operator()( size_t i, size_t j ) noexcept
844 {
845  BLAZE_USER_ASSERT( i<m_, "Invalid row access index" );
846  BLAZE_USER_ASSERT( j<n_, "Invalid column access index" );
847  return v_[i*nn_+j];
848 }
849 //*************************************************************************************************
850 
851 
852 //*************************************************************************************************
862 template< typename Type // Data type of the matrix
863  , bool SO > // Storage order
865  DynamicMatrix<Type,SO>::operator()( size_t i, size_t j ) const noexcept
866 {
867  BLAZE_USER_ASSERT( i<m_, "Invalid row access index" );
868  BLAZE_USER_ASSERT( j<n_, "Invalid column access index" );
869  return v_[i*nn_+j];
870 }
871 //*************************************************************************************************
872 
873 
874 //*************************************************************************************************
885 template< typename Type // Data type of the matrix
886  , bool SO > // Storage order
887 inline typename DynamicMatrix<Type,SO>::Reference
888  DynamicMatrix<Type,SO>::at( size_t i, size_t j )
889 {
890  if( i >= m_ ) {
891  BLAZE_THROW_OUT_OF_RANGE( "Invalid row access index" );
892  }
893  if( j >= n_ ) {
894  BLAZE_THROW_OUT_OF_RANGE( "Invalid column access index" );
895  }
896  return (*this)(i,j);
897 }
898 //*************************************************************************************************
899 
900 
901 //*************************************************************************************************
912 template< typename Type // Data type of the matrix
913  , bool SO > // Storage order
915  DynamicMatrix<Type,SO>::at( size_t i, size_t j ) const
916 {
917  if( i >= m_ ) {
918  BLAZE_THROW_OUT_OF_RANGE( "Invalid row access index" );
919  }
920  if( j >= n_ ) {
921  BLAZE_THROW_OUT_OF_RANGE( "Invalid column access index" );
922  }
923  return (*this)(i,j);
924 }
925 //*************************************************************************************************
926 
927 
928 //*************************************************************************************************
940 template< typename Type // Data type of the matrix
941  , bool SO > // Storage order
942 inline typename DynamicMatrix<Type,SO>::Pointer
944 {
945  return v_;
946 }
947 //*************************************************************************************************
948 
949 
950 //*************************************************************************************************
962 template< typename Type // Data type of the matrix
963  , bool SO > // Storage order
966 {
967  return v_;
968 }
969 //*************************************************************************************************
970 
971 
972 //*************************************************************************************************
980 template< typename Type // Data type of the matrix
981  , bool SO > // Storage order
982 inline typename DynamicMatrix<Type,SO>::Pointer
983  DynamicMatrix<Type,SO>::data( size_t i ) noexcept
984 {
985  BLAZE_USER_ASSERT( i < m_, "Invalid dense matrix row access index" );
986  return v_ + i*nn_;
987 }
988 //*************************************************************************************************
989 
990 
991 //*************************************************************************************************
999 template< typename Type // Data type of the matrix
1000  , bool SO > // Storage order
1002  DynamicMatrix<Type,SO>::data( size_t i ) const noexcept
1003 {
1004  BLAZE_USER_ASSERT( i < m_, "Invalid dense matrix row access index" );
1005  return v_ + i*nn_;
1006 }
1007 //*************************************************************************************************
1008 
1009 
1010 //*************************************************************************************************
1021 template< typename Type // Data type of the matrix
1022  , bool SO > // Storage order
1023 inline typename DynamicMatrix<Type,SO>::Iterator
1024  DynamicMatrix<Type,SO>::begin( size_t i ) noexcept
1025 {
1026  BLAZE_USER_ASSERT( i < m_, "Invalid dense matrix row access index" );
1027  return Iterator( v_ + i*nn_ );
1028 }
1029 //*************************************************************************************************
1030 
1031 
1032 //*************************************************************************************************
1043 template< typename Type // Data type of the matrix
1044  , bool SO > // Storage order
1046  DynamicMatrix<Type,SO>::begin( size_t i ) const noexcept
1047 {
1048  BLAZE_USER_ASSERT( i < m_, "Invalid dense matrix row access index" );
1049  return ConstIterator( v_ + i*nn_ );
1050 }
1051 //*************************************************************************************************
1052 
1053 
1054 //*************************************************************************************************
1065 template< typename Type // Data type of the matrix
1066  , bool SO > // Storage order
1068  DynamicMatrix<Type,SO>::cbegin( size_t i ) const noexcept
1069 {
1070  BLAZE_USER_ASSERT( i < m_, "Invalid dense matrix row access index" );
1071  return ConstIterator( v_ + i*nn_ );
1072 }
1073 //*************************************************************************************************
1074 
1075 
1076 //*************************************************************************************************
1087 template< typename Type // Data type of the matrix
1088  , bool SO > // Storage order
1089 inline typename DynamicMatrix<Type,SO>::Iterator
1090  DynamicMatrix<Type,SO>::end( size_t i ) noexcept
1091 {
1092  BLAZE_USER_ASSERT( i < m_, "Invalid dense matrix row access index" );
1093  return Iterator( v_ + i*nn_ + n_ );
1094 }
1095 //*************************************************************************************************
1096 
1097 
1098 //*************************************************************************************************
1109 template< typename Type // Data type of the matrix
1110  , bool SO > // Storage order
1112  DynamicMatrix<Type,SO>::end( size_t i ) const noexcept
1113 {
1114  BLAZE_USER_ASSERT( i < m_, "Invalid dense matrix row access index" );
1115  return ConstIterator( v_ + i*nn_ + n_ );
1116 }
1117 //*************************************************************************************************
1118 
1119 
1120 //*************************************************************************************************
1131 template< typename Type // Data type of the matrix
1132  , bool SO > // Storage order
1134  DynamicMatrix<Type,SO>::cend( size_t i ) const noexcept
1135 {
1136  BLAZE_USER_ASSERT( i < m_, "Invalid dense matrix row access index" );
1137  return ConstIterator( v_ + i*nn_ + n_ );
1138 }
1139 //*************************************************************************************************
1140 
1141 
1142 
1143 
1144 //=================================================================================================
1145 //
1146 // ASSIGNMENT OPERATORS
1147 //
1148 //=================================================================================================
1149 
1150 //*************************************************************************************************
1156 template< typename Type // Data type of the matrix
1157  , bool SO > // Storage order
1159 {
1160  for( size_t i=0UL; i<m_; ++i )
1161  for( size_t j=0UL; j<n_; ++j )
1162  v_[i*nn_+j] = rhs;
1163 
1164  return *this;
1165 }
1166 //*************************************************************************************************
1167 
1168 
1169 //*************************************************************************************************
1190 template< typename Type // Data type of the matrix
1191  , bool SO > // Storage order
1192 inline DynamicMatrix<Type,SO>&
1194 {
1195  resize( list.size(), determineColumns( list ), false );
1196 
1197  size_t i( 0UL );
1198 
1199  for( const auto& rowList : list ) {
1200  std::fill( std::copy( rowList.begin(), rowList.end(), v_+i*nn_ ), v_+(i+1UL)*nn_, Type() );
1201  ++i;
1202  }
1203 
1204  return *this;
1205 }
1206 //*************************************************************************************************
1207 
1208 
1209 //*************************************************************************************************
1230 template< typename Type // Data type of the matrix
1231  , bool SO > // Storage order
1232 template< typename Other // Data type of the initialization array
1233  , size_t Rows // Number of rows of the initialization array
1234  , size_t Cols > // Number of columns of the initialization array
1235 inline DynamicMatrix<Type,SO>& DynamicMatrix<Type,SO>::operator=( const Other (&array)[Rows][Cols] )
1236 {
1237  resize( Rows, Cols, false );
1238 
1239  for( size_t i=0UL; i<Rows; ++i )
1240  for( size_t j=0UL; j<Cols; ++j )
1241  v_[i*nn_+j] = array[i][j];
1242 
1243  return *this;
1244 }
1245 //*************************************************************************************************
1246 
1247 
1248 //*************************************************************************************************
1257 template< typename Type // Data type of the matrix
1258  , bool SO > // Storage order
1260 {
1261  if( &rhs == this ) return *this;
1262 
1263  resize( rhs.m_, rhs.n_, false );
1264  smpAssign( *this, ~rhs );
1265 
1266  BLAZE_INTERNAL_ASSERT( isIntact(), "Invariant violation detected" );
1267 
1268  return *this;
1269 }
1270 //*************************************************************************************************
1271 
1272 
1273 //*************************************************************************************************
1279 template< typename Type // Data type of the matrix
1280  , bool SO > // Storage order
1282 {
1283  deallocate( v_ );
1284 
1285  m_ = rhs.m_;
1286  n_ = rhs.n_;
1287  nn_ = rhs.nn_;
1288  capacity_ = rhs.capacity_;
1289  v_ = rhs.v_;
1290 
1291  rhs.m_ = 0UL;
1292  rhs.n_ = 0UL;
1293  rhs.nn_ = 0UL;
1294  rhs.capacity_ = 0UL;
1295  rhs.v_ = nullptr;
1296 
1297  return *this;
1298 }
1299 //*************************************************************************************************
1300 
1301 
1302 //*************************************************************************************************
1311 template< typename Type // Data type of the matrix
1312  , bool SO > // Storage order
1313 template< typename MT // Type of the right-hand side matrix
1314  , bool SO2 > // Storage order of the right-hand side matrix
1316 {
1317  using TT = decltype( trans( *this ) );
1318  using CT = decltype( ctrans( *this ) );
1319  using IT = decltype( inv( *this ) );
1320 
1321  if( IsSame_v<MT,TT> && (~rhs).isAliased( this ) ) {
1322  transpose();
1323  }
1324  else if( IsSame_v<MT,CT> && (~rhs).isAliased( this ) ) {
1325  ctranspose();
1326  }
1327  else if( !IsSame_v<MT,IT> && (~rhs).canAlias( this ) ) {
1328  DynamicMatrix tmp( ~rhs );
1329  swap( tmp );
1330  }
1331  else {
1332  resize( (~rhs).rows(), (~rhs).columns(), false );
1333  if( IsSparseMatrix_v<MT> )
1334  reset();
1335  smpAssign( *this, ~rhs );
1336  }
1337 
1338  BLAZE_INTERNAL_ASSERT( isIntact(), "Invariant violation detected" );
1339 
1340  return *this;
1341 }
1342 //*************************************************************************************************
1343 
1344 
1345 //*************************************************************************************************
1355 template< typename Type // Data type of the matrix
1356  , bool SO > // Storage order
1357 template< typename MT // Type of the right-hand side matrix
1358  , bool SO2 > // Storage order of the right-hand side matrix
1360 {
1361  if( (~rhs).rows() != m_ || (~rhs).columns() != n_ ) {
1362  BLAZE_THROW_INVALID_ARGUMENT( "Matrix sizes do not match" );
1363  }
1364 
1365  if( (~rhs).canAlias( this ) ) {
1366  const ResultType_t<MT> tmp( ~rhs );
1367  smpAddAssign( *this, tmp );
1368  }
1369  else {
1370  smpAddAssign( *this, ~rhs );
1371  }
1372 
1373  BLAZE_INTERNAL_ASSERT( isIntact(), "Invariant violation detected" );
1374 
1375  return *this;
1376 }
1377 //*************************************************************************************************
1378 
1379 
1380 //*************************************************************************************************
1390 template< typename Type // Data type of the matrix
1391  , bool SO > // Storage order
1392 template< typename MT // Type of the right-hand side matrix
1393  , bool SO2 > // Storage order of the right-hand side matrix
1395 {
1396  if( (~rhs).rows() != m_ || (~rhs).columns() != n_ ) {
1397  BLAZE_THROW_INVALID_ARGUMENT( "Matrix sizes do not match" );
1398  }
1399 
1400  if( (~rhs).canAlias( this ) ) {
1401  const ResultType_t<MT> tmp( ~rhs );
1402  smpSubAssign( *this, tmp );
1403  }
1404  else {
1405  smpSubAssign( *this, ~rhs );
1406  }
1407 
1408  BLAZE_INTERNAL_ASSERT( isIntact(), "Invariant violation detected" );
1409 
1410  return *this;
1411 }
1412 //*************************************************************************************************
1413 
1414 
1415 //*************************************************************************************************
1425 template< typename Type // Data type of the matrix
1426  , bool SO > // Storage order
1427 template< typename MT // Type of the right-hand side matrix
1428  , bool SO2 > // Storage order of the right-hand side matrix
1430 {
1431  if( (~rhs).rows() != m_ || (~rhs).columns() != n_ ) {
1432  BLAZE_THROW_INVALID_ARGUMENT( "Matrix sizes do not match" );
1433  }
1434 
1435  if( (~rhs).canAlias( this ) ) {
1436  const ResultType_t<MT> tmp( ~rhs );
1437  smpSchurAssign( *this, tmp );
1438  }
1439  else {
1440  smpSchurAssign( *this, ~rhs );
1441  }
1442 
1443  BLAZE_INTERNAL_ASSERT( isIntact(), "Invariant violation detected" );
1444 
1445  return *this;
1446 }
1447 //*************************************************************************************************
1448 
1449 
1450 
1451 
1452 //=================================================================================================
1453 //
1454 // UTILITY FUNCTIONS
1455 //
1456 //=================================================================================================
1457 
1458 //*************************************************************************************************
1463 template< typename Type // Data type of the matrix
1464  , bool SO > // Storage order
1465 inline size_t DynamicMatrix<Type,SO>::rows() const noexcept
1466 {
1467  return m_;
1468 }
1469 //*************************************************************************************************
1470 
1471 
1472 //*************************************************************************************************
1477 template< typename Type // Data type of the matrix
1478  , bool SO > // Storage order
1479 inline size_t DynamicMatrix<Type,SO>::columns() const noexcept
1480 {
1481  return n_;
1482 }
1483 //*************************************************************************************************
1484 
1485 
1486 //*************************************************************************************************
1496 template< typename Type // Data type of the matrix
1497  , bool SO > // Storage order
1498 inline size_t DynamicMatrix<Type,SO>::spacing() const noexcept
1499 {
1500  return nn_;
1501 }
1502 //*************************************************************************************************
1503 
1504 
1505 //*************************************************************************************************
1510 template< typename Type // Data type of the matrix
1511  , bool SO > // Storage order
1512 inline size_t DynamicMatrix<Type,SO>::capacity() const noexcept
1513 {
1514  return capacity_;
1515 }
1516 //*************************************************************************************************
1517 
1518 
1519 //*************************************************************************************************
1530 template< typename Type // Data type of the matrix
1531  , bool SO > // Storage order
1532 inline size_t DynamicMatrix<Type,SO>::capacity( size_t i ) const noexcept
1533 {
1534  UNUSED_PARAMETER( i );
1535  BLAZE_USER_ASSERT( i < rows(), "Invalid row access index" );
1536  return nn_;
1537 }
1538 //*************************************************************************************************
1539 
1540 
1541 //*************************************************************************************************
1546 template< typename Type // Data type of the matrix
1547  , bool SO > // Storage order
1549 {
1550  size_t nonzeros( 0UL );
1551 
1552  for( size_t i=0UL; i<m_; ++i )
1553  for( size_t j=0UL; j<n_; ++j )
1554  if( !isDefault( v_[i*nn_+j] ) )
1555  ++nonzeros;
1556 
1557  return nonzeros;
1558 }
1559 //*************************************************************************************************
1560 
1561 
1562 //*************************************************************************************************
1573 template< typename Type // Data type of the matrix
1574  , bool SO > // Storage order
1575 inline size_t DynamicMatrix<Type,SO>::nonZeros( size_t i ) const
1576 {
1577  BLAZE_USER_ASSERT( i < rows(), "Invalid row access index" );
1578 
1579  const size_t jend( i*nn_ + n_ );
1580  size_t nonzeros( 0UL );
1581 
1582  for( size_t j=i*nn_; j<jend; ++j )
1583  if( !isDefault( v_[j] ) )
1584  ++nonzeros;
1585 
1586  return nonzeros;
1587 }
1588 //*************************************************************************************************
1589 
1590 
1591 //*************************************************************************************************
1596 template< typename Type // Data type of the matrix
1597  , bool SO > // Storage order
1599 {
1600  using blaze::clear;
1601 
1602  for( size_t i=0UL; i<m_; ++i )
1603  for( size_t j=0UL; j<n_; ++j )
1604  clear( v_[i*nn_+j] );
1605 }
1606 //*************************************************************************************************
1607 
1608 
1609 //*************************************************************************************************
1620 template< typename Type // Data type of the matrix
1621  , bool SO > // Storage order
1622 inline void DynamicMatrix<Type,SO>::reset( size_t i )
1623 {
1624  using blaze::clear;
1625 
1626  BLAZE_USER_ASSERT( i < rows(), "Invalid row access index" );
1627  for( size_t j=0UL; j<n_; ++j )
1628  clear( v_[i*nn_+j] );
1629 }
1630 //*************************************************************************************************
1631 
1632 
1633 //*************************************************************************************************
1640 template< typename Type // Data type of the matrix
1641  , bool SO > // Storage order
1643 {
1644  resize( 0UL, 0UL, false );
1645 }
1646 //*************************************************************************************************
1647 
1648 
1649 //*************************************************************************************************
1683 template< typename Type // Data type of the matrix
1684  , bool SO > // Storage order
1685 void DynamicMatrix<Type,SO>::resize( size_t m, size_t n, bool preserve )
1686 {
1687  using std::swap;
1688  using blaze::min;
1689 
1690  if( m == m_ && n == n_ ) return;
1691 
1692  const size_t nn( addPadding( n ) );
1693 
1694  if( preserve )
1695  {
1696  Type* BLAZE_RESTRICT v = allocate<Type>( m*nn );
1697  const size_t min_m( min( m, m_ ) );
1698  const size_t min_n( min( n, n_ ) );
1699 
1700  for( size_t i=0UL; i<min_m; ++i ) {
1701  transfer( v_+i*nn_, v_+i*nn_+min_n, v+i*nn );
1702  }
1703 
1704  swap( v_, v );
1705  deallocate( v );
1706  capacity_ = m*nn;
1707  }
1708  else if( m*nn > capacity_ ) {
1709  Type* BLAZE_RESTRICT v = allocate<Type>( m*nn );
1710  swap( v_, v );
1711  deallocate( v );
1712  capacity_ = m*nn;
1713  }
1714 
1715  if( IsVectorizable_v<Type> ) {
1716  for( size_t i=0UL; i<m; ++i )
1717  for( size_t j=n; j<nn; ++j )
1718  v_[i*nn+j] = Type();
1719  }
1720 
1721  m_ = m;
1722  n_ = n;
1723  nn_ = nn;
1724 }
1725 //*************************************************************************************************
1726 
1727 
1728 //*************************************************************************************************
1742 template< typename Type // Data type of the matrix
1743  , bool SO > // Storage order
1744 inline void DynamicMatrix<Type,SO>::extend( size_t m, size_t n, bool preserve )
1745 {
1746  resize( m_+m, n_+n, preserve );
1747 }
1748 //*************************************************************************************************
1749 
1750 
1751 //*************************************************************************************************
1760 template< typename Type // Data type of the matrix
1761  , bool SO > // Storage order
1763 {
1764  using std::swap;
1765 
1766  if( elements > capacity_ )
1767  {
1768  // Allocating a new array
1769  Type* BLAZE_RESTRICT tmp = allocate<Type>( elements );
1770 
1771  // Initializing the new array
1772  transfer( v_, v_+capacity_, tmp );
1773 
1774  if( IsVectorizable_v<Type> ) {
1775  for( size_t i=capacity_; i<elements; ++i )
1776  tmp[i] = Type();
1777  }
1778 
1779  // Replacing the old array
1780  swap( tmp, v_ );
1781  deallocate( tmp );
1782  capacity_ = elements;
1783  }
1784 }
1785 //*************************************************************************************************
1786 
1787 
1788 //*************************************************************************************************
1798 template< typename Type // Data type of the matrix
1799  , bool SO > // Storage order
1801 {
1802  if( ( m_ * nn_ ) < capacity_ ) {
1803  DynamicMatrix( *this ).swap( *this );
1804  }
1805 }
1806 //*************************************************************************************************
1807 
1808 
1809 //*************************************************************************************************
1815 template< typename Type // Data type of the matrix
1816  , bool SO > // Storage order
1818 {
1819  using std::swap;
1820 
1821  swap( m_ , m.m_ );
1822  swap( n_ , m.n_ );
1823  swap( nn_, m.nn_ );
1824  swap( capacity_, m.capacity_ );
1825  swap( v_ , m.v_ );
1826 }
1827 //*************************************************************************************************
1828 
1829 
1830 //*************************************************************************************************
1839 template< typename Type // Data type of the matrix
1840  , bool SO > // Storage order
1841 inline size_t DynamicMatrix<Type,SO>::addPadding( size_t value ) const noexcept
1842 {
1843  if( usePadding && IsVectorizable_v<Type> )
1844  return nextMultiple<size_t>( value, SIMDSIZE );
1845  else return value;
1846 }
1847 //*************************************************************************************************
1848 
1849 
1850 
1851 
1852 //=================================================================================================
1853 //
1854 // NUMERIC FUNCTIONS
1855 //
1856 //=================================================================================================
1857 
1858 //*************************************************************************************************
1863 template< typename Type // Data type of the matrix
1864  , bool SO > // Storage order
1866 {
1867  using std::swap;
1868 
1869  constexpr size_t block( BLOCK_SIZE );
1870 
1871  if( m_ == n_ )
1872  {
1873  for( size_t ii=0UL; ii<m_; ii+=block ) {
1874  const size_t iend( min( ii+block, m_ ) );
1875  for( size_t jj=0UL; jj<=ii; jj+=block ) {
1876  for( size_t i=ii; i<iend; ++i ) {
1877  const size_t jend( min( jj+block, n_, i ) );
1878  for( size_t j=jj; j<jend; ++j ) {
1879  swap( v_[i*nn_+j], v_[j*nn_+i] );
1880  }
1881  }
1882  }
1883  }
1884  }
1885  else
1886  {
1887  DynamicMatrix tmp( trans(*this) );
1888  this->swap( tmp );
1889  }
1890 
1891  return *this;
1892 }
1893 //*************************************************************************************************
1894 
1895 
1896 //*************************************************************************************************
1901 template< typename Type // Data type of the matrix
1902  , bool SO > // Storage order
1904 {
1905  constexpr size_t block( BLOCK_SIZE );
1906 
1907  if( m_ == n_ )
1908  {
1909  for( size_t ii=0UL; ii<m_; ii+=block ) {
1910  const size_t iend( min( ii+block, m_ ) );
1911  for( size_t jj=0UL; jj<ii; jj+=block ) {
1912  const size_t jend( min( jj+block, n_ ) );
1913  for( size_t i=ii; i<iend; ++i ) {
1914  for( size_t j=jj; j<jend; ++j ) {
1915  cswap( v_[i*nn_+j], v_[j*nn_+i] );
1916  }
1917  }
1918  }
1919  for( size_t i=ii; i<iend; ++i ) {
1920  for( size_t j=ii; j<i; ++j ) {
1921  cswap( v_[i*nn_+j], v_[j*nn_+i] );
1922  }
1923  conjugate( v_[i*nn_+i] );
1924  }
1925  }
1926  }
1927  else
1928  {
1929  DynamicMatrix tmp( ctrans(*this) );
1930  swap( tmp );
1931  }
1932 
1933  return *this;
1934 }
1935 //*************************************************************************************************
1936 
1937 
1938 //*************************************************************************************************
1955 template< typename Type // Data type of the matrix
1956  , bool SO > // Storage order
1957 template< typename Other > // Data type of the scalar value
1959 {
1960  for( size_t i=0UL; i<m_; ++i )
1961  for( size_t j=0UL; j<n_; ++j )
1962  v_[i*nn_+j] *= scalar;
1963 
1964  return *this;
1965 }
1966 //*************************************************************************************************
1967 
1968 
1969 
1970 
1971 //=================================================================================================
1972 //
1973 // DEBUGGING FUNCTIONS
1974 //
1975 //=================================================================================================
1976 
1977 //*************************************************************************************************
1986 template< typename Type // Data type of the matrix
1987  , bool SO > // Storage order
1988 inline bool DynamicMatrix<Type,SO>::isIntact() const noexcept
1989 {
1990  if( m_ * n_ > capacity_ )
1991  return false;
1992 
1993  if( IsVectorizable_v<Type> ) {
1994  for( size_t i=0UL; i<m_; ++i ) {
1995  for( size_t j=n_; j<nn_; ++j ) {
1996  if( v_[i*nn_+j] != Type() )
1997  return false;
1998  }
1999  }
2000  }
2001 
2002  return true;
2003 }
2004 //*************************************************************************************************
2005 
2006 
2007 
2008 
2009 //=================================================================================================
2010 //
2011 // EXPRESSION TEMPLATE EVALUATION FUNCTIONS
2012 //
2013 //=================================================================================================
2014 
2015 //*************************************************************************************************
2025 template< typename Type // Data type of the matrix
2026  , bool SO > // Storage order
2027 template< typename Other > // Data type of the foreign expression
2028 inline bool DynamicMatrix<Type,SO>::canAlias( const Other* alias ) const noexcept
2029 {
2030  return static_cast<const void*>( this ) == static_cast<const void*>( alias );
2031 }
2032 //*************************************************************************************************
2033 
2034 
2035 //*************************************************************************************************
2045 template< typename Type // Data type of the matrix
2046  , bool SO > // Storage order
2047 template< typename Other > // Data type of the foreign expression
2048 inline bool DynamicMatrix<Type,SO>::isAliased( const Other* alias ) const noexcept
2049 {
2050  return static_cast<const void*>( this ) == static_cast<const void*>( alias );
2051 }
2052 //*************************************************************************************************
2053 
2054 
2055 //*************************************************************************************************
2064 template< typename Type // Data type of the matrix
2065  , bool SO > // Storage order
2066 inline bool DynamicMatrix<Type,SO>::isAligned() const noexcept
2067 {
2068  return ( usePadding || columns() % SIMDSIZE == 0UL );
2069 }
2070 //*************************************************************************************************
2071 
2072 
2073 //*************************************************************************************************
2083 template< typename Type // Data type of the matrix
2084  , bool SO > // Storage order
2085 inline bool DynamicMatrix<Type,SO>::canSMPAssign() const noexcept
2086 {
2087  return ( rows() * columns() >= SMP_DMATASSIGN_THRESHOLD );
2088 }
2089 //*************************************************************************************************
2090 
2091 
2092 //*************************************************************************************************
2107 template< typename Type // Data type of the matrix
2108  , bool SO > // Storage order
2110  DynamicMatrix<Type,SO>::load( size_t i, size_t j ) const noexcept
2111 {
2112  if( usePadding )
2113  return loada( i, j );
2114  else
2115  return loadu( i, j );
2116 }
2117 //*************************************************************************************************
2118 
2119 
2120 //*************************************************************************************************
2135 template< typename Type // Data type of the matrix
2136  , bool SO > // Storage order
2138  DynamicMatrix<Type,SO>::loada( size_t i, size_t j ) const noexcept
2139 {
2140  using blaze::loada;
2141 
2143 
2144  BLAZE_INTERNAL_ASSERT( i < m_, "Invalid row access index" );
2145  BLAZE_INTERNAL_ASSERT( j < n_, "Invalid column access index" );
2146  BLAZE_INTERNAL_ASSERT( j + SIMDSIZE <= nn_, "Invalid column access index" );
2147  BLAZE_INTERNAL_ASSERT( !usePadding || j % SIMDSIZE == 0UL, "Invalid column access index" );
2148  BLAZE_INTERNAL_ASSERT( checkAlignment( v_+i*nn_+j ), "Invalid alignment detected" );
2149 
2150  return loada( v_+i*nn_+j );
2151 }
2152 //*************************************************************************************************
2153 
2154 
2155 //*************************************************************************************************
2170 template< typename Type // Data type of the matrix
2171  , bool SO > // Storage order
2173  DynamicMatrix<Type,SO>::loadu( size_t i, size_t j ) const noexcept
2174 {
2175  using blaze::loadu;
2176 
2178 
2179  BLAZE_INTERNAL_ASSERT( i < m_, "Invalid row access index" );
2180  BLAZE_INTERNAL_ASSERT( j < n_, "Invalid column access index" );
2181  BLAZE_INTERNAL_ASSERT( j + SIMDSIZE <= nn_, "Invalid column access index" );
2182 
2183  return loadu( v_+i*nn_+j );
2184 }
2185 //*************************************************************************************************
2186 
2187 
2188 //*************************************************************************************************
2204 template< typename Type // Data type of the matrix
2205  , bool SO > // Storage order
2207  DynamicMatrix<Type,SO>::store( size_t i, size_t j, const SIMDType& value ) noexcept
2208 {
2209  if( usePadding )
2210  storea( i, j, value );
2211  else
2212  storeu( i, j, value );
2213 }
2214 //*************************************************************************************************
2215 
2216 
2217 //*************************************************************************************************
2233 template< typename Type // Data type of the matrix
2234  , bool SO > // Storage order
2236  DynamicMatrix<Type,SO>::storea( size_t i, size_t j, const SIMDType& value ) noexcept
2237 {
2238  using blaze::storea;
2239 
2241 
2242  BLAZE_INTERNAL_ASSERT( i < m_, "Invalid row access index" );
2243  BLAZE_INTERNAL_ASSERT( j < n_, "Invalid column access index" );
2244  BLAZE_INTERNAL_ASSERT( j + SIMDSIZE <= nn_, "Invalid column access index" );
2245  BLAZE_INTERNAL_ASSERT( !usePadding || j % SIMDSIZE == 0UL, "Invalid column access index" );
2246  BLAZE_INTERNAL_ASSERT( checkAlignment( v_+i*nn_+j ), "Invalid alignment detected" );
2247 
2248  storea( v_+i*nn_+j, value );
2249 }
2250 //*************************************************************************************************
2251 
2252 
2253 //*************************************************************************************************
2269 template< typename Type // Data type of the matrix
2270  , bool SO > // Storage order
2272  DynamicMatrix<Type,SO>::storeu( size_t i, size_t j, const SIMDType& value ) noexcept
2273 {
2274  using blaze::storeu;
2275 
2277 
2278  BLAZE_INTERNAL_ASSERT( i < m_, "Invalid row access index" );
2279  BLAZE_INTERNAL_ASSERT( j < n_, "Invalid column access index" );
2280  BLAZE_INTERNAL_ASSERT( j + SIMDSIZE <= nn_, "Invalid column access index" );
2281 
2282  storeu( v_+i*nn_+j, value );
2283 }
2284 //*************************************************************************************************
2285 
2286 
2287 //*************************************************************************************************
2304 template< typename Type // Data type of the matrix
2305  , bool SO > // Storage order
2307  DynamicMatrix<Type,SO>::stream( size_t i, size_t j, const SIMDType& value ) noexcept
2308 {
2309  using blaze::stream;
2310 
2312 
2313  BLAZE_INTERNAL_ASSERT( i < m_, "Invalid row access index" );
2314  BLAZE_INTERNAL_ASSERT( j < n_, "Invalid column access index" );
2315  BLAZE_INTERNAL_ASSERT( j + SIMDSIZE <= nn_, "Invalid column access index" );
2316  BLAZE_INTERNAL_ASSERT( !usePadding || j % SIMDSIZE == 0UL, "Invalid column access index" );
2317  BLAZE_INTERNAL_ASSERT( checkAlignment( v_+i*nn_+j ), "Invalid alignment detected" );
2318 
2319  stream( v_+i*nn_+j, value );
2320 }
2321 //*************************************************************************************************
2322 
2323 
2324 //*************************************************************************************************
2335 template< typename Type // Data type of the matrix
2336  , bool SO > // Storage order
2337 template< typename MT > // Type of the right-hand side dense matrix
2340 {
2341  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
2342  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
2343 
2344  const size_t jpos( n_ & size_t(-2) );
2345  BLAZE_INTERNAL_ASSERT( ( n_ - ( n_ % 2UL ) ) == jpos, "Invalid end calculation" );
2346 
2347  for( size_t i=0UL; i<m_; ++i ) {
2348  for( size_t j=0UL; j<jpos; j+=2UL ) {
2349  v_[i*nn_+j ] = (~rhs)(i,j );
2350  v_[i*nn_+j+1UL] = (~rhs)(i,j+1UL);
2351  }
2352  if( jpos < n_ ) {
2353  v_[i*nn_+jpos] = (~rhs)(i,jpos);
2354  }
2355  }
2356 }
2357 //*************************************************************************************************
2358 
2359 
2360 //*************************************************************************************************
2371 template< typename Type // Data type of the matrix
2372  , bool SO > // Storage order
2373 template< typename MT > // Type of the right-hand side dense matrix
2374 inline auto DynamicMatrix<Type,SO>::assign( const DenseMatrix<MT,SO>& rhs )
2376 {
2378 
2379  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
2380  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
2381 
2382  constexpr bool remainder( !usePadding || !IsPadded_v<MT> );
2383 
2384  const size_t jpos( ( remainder )?( n_ & size_t(-SIMDSIZE) ):( n_ ) );
2385  BLAZE_INTERNAL_ASSERT( !remainder || ( n_ - ( n_ % (SIMDSIZE) ) ) == jpos, "Invalid end calculation" );
2386 
2387  if( usePadding && useStreaming &&
2388  ( m_*n_ > ( cacheSize / ( sizeof(Type) * 3UL ) ) ) && !(~rhs).isAliased( this ) )
2389  {
2390  for( size_t i=0UL; i<m_; ++i )
2391  {
2392  size_t j( 0UL );
2393  Iterator left( begin(i) );
2394  ConstIterator_t<MT> right( (~rhs).begin(i) );
2395 
2396  for( ; j<jpos; j+=SIMDSIZE, left+=SIMDSIZE, right+=SIMDSIZE ) {
2397  left.stream( right.load() );
2398  }
2399  for( ; remainder && j<n_; ++j, ++left, ++right ) {
2400  *left = *right;
2401  }
2402  }
2403  }
2404  else
2405  {
2406  for( size_t i=0UL; i<m_; ++i )
2407  {
2408  size_t j( 0UL );
2409  Iterator left( begin(i) );
2410  ConstIterator_t<MT> right( (~rhs).begin(i) );
2411 
2412  for( ; (j+SIMDSIZE*3UL) < jpos; j+=SIMDSIZE*4UL ) {
2413  left.store( right.load() ); left += SIMDSIZE; right += SIMDSIZE;
2414  left.store( right.load() ); left += SIMDSIZE; right += SIMDSIZE;
2415  left.store( right.load() ); left += SIMDSIZE; right += SIMDSIZE;
2416  left.store( right.load() ); left += SIMDSIZE; right += SIMDSIZE;
2417  }
2418  for( ; j<jpos; j+=SIMDSIZE ) {
2419  left.store( right.load() ); left+=SIMDSIZE, right+=SIMDSIZE;
2420  }
2421  for( ; remainder && j<n_; ++j ) {
2422  *left = *right; ++left; ++right;
2423  }
2424  }
2425  }
2426 }
2427 //*************************************************************************************************
2428 
2429 
2430 //*************************************************************************************************
2441 template< typename Type // Data type of the matrix
2442  , bool SO > // Storage order
2443 template< typename MT > // Type of the right-hand side dense matrix
2445 {
2447 
2448  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
2449  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
2450 
2451  constexpr size_t block( BLOCK_SIZE );
2452 
2453  for( size_t ii=0UL; ii<m_; ii+=block ) {
2454  const size_t iend( min( m_, ii+block ) );
2455  for( size_t jj=0UL; jj<n_; jj+=block ) {
2456  const size_t jend( min( n_, jj+block ) );
2457  for( size_t i=ii; i<iend; ++i ) {
2458  for( size_t j=jj; j<jend; ++j ) {
2459  v_[i*nn_+j] = (~rhs)(i,j);
2460  }
2461  }
2462  }
2463  }
2464 }
2465 //*************************************************************************************************
2466 
2467 
2468 //*************************************************************************************************
2479 template< typename Type // Data type of the matrix
2480  , bool SO > // Storage order
2481 template< typename MT > // Type of the right-hand side sparse matrix
2483 {
2484  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
2485  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
2486 
2487  for( size_t i=0UL; i<m_; ++i )
2488  for( auto element=(~rhs).begin(i); element!=(~rhs).end(i); ++element )
2489  v_[i*nn_+element->index()] = element->value();
2490 }
2491 //*************************************************************************************************
2492 
2493 
2494 //*************************************************************************************************
2505 template< typename Type // Data type of the matrix
2506  , bool SO > // Storage order
2507 template< typename MT > // Type of the right-hand side sparse matrix
2509 {
2511 
2512  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
2513  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
2514 
2515  for( size_t j=0UL; j<n_; ++j )
2516  for( auto element=(~rhs).begin(j); element!=(~rhs).end(j); ++element )
2517  v_[element->index()*nn_+j] = element->value();
2518 }
2519 //*************************************************************************************************
2520 
2521 
2522 //*************************************************************************************************
2533 template< typename Type // Data type of the matrix
2534  , bool SO > // Storage order
2535 template< typename MT > // Type of the right-hand side dense matrix
2538 {
2539  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
2540  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
2541 
2542  for( size_t i=0UL; i<m_; ++i )
2543  {
2544  if( IsDiagonal_v<MT> )
2545  {
2546  v_[i*nn_+i] += (~rhs)(i,i);
2547  }
2548  else
2549  {
2550  const size_t jbegin( ( IsUpper_v<MT> )
2551  ?( IsStrictlyUpper_v<MT> ? i+1UL : i )
2552  :( 0UL ) );
2553  const size_t jend ( ( IsLower_v<MT> )
2554  ?( IsStrictlyLower_v<MT> ? i : i+1UL )
2555  :( n_ ) );
2556  BLAZE_INTERNAL_ASSERT( jbegin <= jend, "Invalid loop indices detected" );
2557 
2558  size_t j( jbegin );
2559 
2560  for( ; (j+2UL) <= jend; j+=2UL ) {
2561  v_[i*nn_+j ] += (~rhs)(i,j );
2562  v_[i*nn_+j+1UL] += (~rhs)(i,j+1UL);
2563  }
2564  if( j < jend ) {
2565  v_[i*nn_+j] += (~rhs)(i,j);
2566  }
2567  }
2568  }
2569 }
2570 //*************************************************************************************************
2571 
2572 
2573 //*************************************************************************************************
2584 template< typename Type // Data type of the matrix
2585  , bool SO > // Storage order
2586 template< typename MT > // Type of the right-hand side dense matrix
2587 inline auto DynamicMatrix<Type,SO>::addAssign( const DenseMatrix<MT,SO>& rhs )
2589 {
2592 
2593  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
2594  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
2595 
2596  constexpr bool remainder( !usePadding || !IsPadded_v<MT> );
2597 
2598  for( size_t i=0UL; i<m_; ++i )
2599  {
2600  const size_t jbegin( ( IsUpper_v<MT> )
2601  ?( ( IsStrictlyUpper_v<MT> ? i+1UL : i ) & size_t(-SIMDSIZE) )
2602  :( 0UL ) );
2603  const size_t jend ( ( IsLower_v<MT> )
2604  ?( IsStrictlyLower_v<MT> ? i : i+1UL )
2605  :( n_ ) );
2606  BLAZE_INTERNAL_ASSERT( jbegin <= jend, "Invalid loop indices detected" );
2607 
2608  const size_t jpos( ( remainder )?( jend & size_t(-SIMDSIZE) ):( jend ) );
2609  BLAZE_INTERNAL_ASSERT( !remainder || ( jend - ( jend % (SIMDSIZE) ) ) == jpos, "Invalid end calculation" );
2610 
2611  size_t j( jbegin );
2612  Iterator left( begin(i) + jbegin );
2613  ConstIterator_t<MT> right( (~rhs).begin(i) + jbegin );
2614 
2615  for( ; (j+SIMDSIZE*3UL) < jpos; j+=SIMDSIZE*4UL ) {
2616  left.store( left.load() + right.load() ); left += SIMDSIZE; right += SIMDSIZE;
2617  left.store( left.load() + right.load() ); left += SIMDSIZE; right += SIMDSIZE;
2618  left.store( left.load() + right.load() ); left += SIMDSIZE; right += SIMDSIZE;
2619  left.store( left.load() + right.load() ); left += SIMDSIZE; right += SIMDSIZE;
2620  }
2621  for( ; j<jpos; j+=SIMDSIZE ) {
2622  left.store( left.load() + right.load() ); left += SIMDSIZE; right += SIMDSIZE;
2623  }
2624  for( ; remainder && j<jend; ++j ) {
2625  *left += *right; ++left; ++right;
2626  }
2627  }
2628 }
2629 //*************************************************************************************************
2630 
2631 
2632 //*************************************************************************************************
2643 template< typename Type // Data type of the matrix
2644  , bool SO > // Storage order
2645 template< typename MT > // Type of the right-hand side dense matrix
2647 {
2649 
2650  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
2651  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
2652 
2653  constexpr size_t block( BLOCK_SIZE );
2654 
2655  for( size_t ii=0UL; ii<m_; ii+=block ) {
2656  const size_t iend( min( m_, ii+block ) );
2657  for( size_t jj=0UL; jj<n_; jj+=block )
2658  {
2659  if( IsLower_v<MT> && ii < jj ) break;
2660  if( IsUpper_v<MT> && ii > jj ) continue;
2661 
2662  for( size_t i=ii; i<iend; ++i )
2663  {
2664  const size_t jbegin( ( IsUpper_v<MT> )
2665  ?( max( ( IsStrictlyUpper_v<MT> ? i+1UL : i ), jj ) )
2666  :( jj ) );
2667  const size_t jend ( ( IsLower_v<MT> )
2668  ?( min( ( IsStrictlyLower_v<MT> ? i : i+1UL ), n_, jj+block ) )
2669  :( min( n_, jj+block ) ) );
2670  BLAZE_INTERNAL_ASSERT( jbegin <= jend, "Invalid loop indices detected" );
2671 
2672  for( size_t j=jbegin; j<jend; ++j ) {
2673  v_[i*nn_+j] += (~rhs)(i,j);
2674  }
2675  }
2676  }
2677  }
2678 }
2679 //*************************************************************************************************
2680 
2681 
2682 //*************************************************************************************************
2693 template< typename Type // Data type of the matrix
2694  , bool SO > // Storage order
2695 template< typename MT > // Type of the right-hand side sparse matrix
2697 {
2698  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
2699  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
2700 
2701  for( size_t i=0UL; i<m_; ++i )
2702  for( auto element=(~rhs).begin(i); element!=(~rhs).end(i); ++element )
2703  v_[i*nn_+element->index()] += element->value();
2704 }
2705 //*************************************************************************************************
2706 
2707 
2708 //*************************************************************************************************
2719 template< typename Type // Data type of the matrix
2720  , bool SO > // Storage order
2721 template< typename MT > // Type of the right-hand side sparse matrix
2723 {
2725 
2726  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
2727  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
2728 
2729  for( size_t j=0UL; j<n_; ++j )
2730  for( auto element=(~rhs).begin(j); element!=(~rhs).end(j); ++element )
2731  v_[element->index()*nn_+j] += element->value();
2732 }
2733 //*************************************************************************************************
2734 
2735 
2736 //*************************************************************************************************
2747 template< typename Type // Data type of the matrix
2748  , bool SO > // Storage order
2749 template< typename MT > // Type of the right-hand side dense matrix
2752 {
2753  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
2754  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
2755 
2756  for( size_t i=0UL; i<m_; ++i )
2757  {
2758  if( IsDiagonal_v<MT> )
2759  {
2760  v_[i*nn_+i] -= (~rhs)(i,i);
2761  }
2762  else
2763  {
2764  const size_t jbegin( ( IsUpper_v<MT> )
2765  ?( IsStrictlyUpper_v<MT> ? i+1UL : i )
2766  :( 0UL ) );
2767  const size_t jend ( ( IsLower_v<MT> )
2768  ?( IsStrictlyLower_v<MT> ? i : i+1UL )
2769  :( n_ ) );
2770  BLAZE_INTERNAL_ASSERT( jbegin <= jend, "Invalid loop indices detected" );
2771 
2772  size_t j( jbegin );
2773 
2774  for( ; (j+2UL) <= jend; j+=2UL ) {
2775  v_[i*nn_+j ] -= (~rhs)(i,j );
2776  v_[i*nn_+j+1UL] -= (~rhs)(i,j+1UL);
2777  }
2778  if( j < jend ) {
2779  v_[i*nn_+j] -= (~rhs)(i,j);
2780  }
2781  }
2782  }
2783 }
2784 //*************************************************************************************************
2785 
2786 
2787 //*************************************************************************************************
2798 template< typename Type // Data type of the matrix
2799  , bool SO > // Storage order
2800 template< typename MT > // Type of the right-hand side dense matrix
2801 inline auto DynamicMatrix<Type,SO>::subAssign( const DenseMatrix<MT,SO>& rhs )
2803 {
2806 
2807  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
2808  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
2809 
2810  constexpr bool remainder( !usePadding || !IsPadded_v<MT> );
2811 
2812  for( size_t i=0UL; i<m_; ++i )
2813  {
2814  const size_t jbegin( ( IsUpper_v<MT> )
2815  ?( ( IsStrictlyUpper_v<MT> ? i+1UL : i ) & size_t(-SIMDSIZE) )
2816  :( 0UL ) );
2817  const size_t jend ( ( IsLower_v<MT> )
2818  ?( IsStrictlyLower_v<MT> ? i : i+1UL )
2819  :( n_ ) );
2820  BLAZE_INTERNAL_ASSERT( jbegin <= jend, "Invalid loop indices detected" );
2821 
2822  const size_t jpos( ( remainder )?( jend & size_t(-SIMDSIZE) ):( jend ) );
2823  BLAZE_INTERNAL_ASSERT( !remainder || ( jend - ( jend % (SIMDSIZE) ) ) == jpos, "Invalid end calculation" );
2824 
2825  size_t j( jbegin );
2826  Iterator left( begin(i) + jbegin );
2827  ConstIterator_t<MT> right( (~rhs).begin(i) + jbegin );
2828 
2829  for( ; (j+SIMDSIZE*3UL) < jpos; j+=SIMDSIZE*4UL ) {
2830  left.store( left.load() - right.load() ); left += SIMDSIZE; right += SIMDSIZE;
2831  left.store( left.load() - right.load() ); left += SIMDSIZE; right += SIMDSIZE;
2832  left.store( left.load() - right.load() ); left += SIMDSIZE; right += SIMDSIZE;
2833  left.store( left.load() - right.load() ); left += SIMDSIZE; right += SIMDSIZE;
2834  }
2835  for( ; j<jpos; j+=SIMDSIZE ) {
2836  left.store( left.load() - right.load() ); left += SIMDSIZE; right += SIMDSIZE;
2837  }
2838  for( ; remainder && j<jend; ++j ) {
2839  *left -= *right; ++left; ++right;
2840  }
2841  }
2842 }
2843 //*************************************************************************************************
2844 
2845 
2846 //*************************************************************************************************
2857 template< typename Type // Data type of the matrix
2858  , bool SO > // Storage order
2859 template< typename MT > // Type of the right-hand side dense matrix
2861 {
2863 
2864  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
2865  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
2866 
2867  constexpr size_t block( BLOCK_SIZE );
2868 
2869  for( size_t ii=0UL; ii<m_; ii+=block ) {
2870  const size_t iend( min( m_, ii+block ) );
2871  for( size_t jj=0UL; jj<n_; jj+=block )
2872  {
2873  if( IsLower_v<MT> && ii < jj ) break;
2874  if( IsUpper_v<MT> && ii > jj ) continue;
2875 
2876  for( size_t i=ii; i<iend; ++i )
2877  {
2878  const size_t jbegin( ( IsUpper_v<MT> )
2879  ?( max( ( IsStrictlyUpper_v<MT> ? i+1UL : i ), jj ) )
2880  :( jj ) );
2881  const size_t jend ( ( IsLower_v<MT> )
2882  ?( min( ( IsStrictlyLower_v<MT> ? i : i+1UL ), n_, jj+block ) )
2883  :( min( n_, jj+block ) ) );
2884  BLAZE_INTERNAL_ASSERT( jbegin <= jend, "Invalid loop indices detected" );
2885 
2886  for( size_t j=jbegin; j<jend; ++j ) {
2887  v_[i*nn_+j] -= (~rhs)(i,j);
2888  }
2889  }
2890  }
2891  }
2892 }
2893 //*************************************************************************************************
2894 
2895 
2896 //*************************************************************************************************
2907 template< typename Type // Data type of the matrix
2908  , bool SO > // Storage order
2909 template< typename MT > // Type of the right-hand side sparse matrix
2911 {
2912  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
2913  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
2914 
2915  for( size_t i=0UL; i<m_; ++i )
2916  for( auto element=(~rhs).begin(i); element!=(~rhs).end(i); ++element )
2917  v_[i*nn_+element->index()] -= element->value();
2918 }
2919 //*************************************************************************************************
2920 
2921 
2922 //*************************************************************************************************
2933 template< typename Type // Data type of the matrix
2934  , bool SO > // Storage order
2935 template< typename MT > // Type of the right-hand side sparse matrix
2937 {
2939 
2940  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
2941  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
2942 
2943  for( size_t j=0UL; j<n_; ++j )
2944  for( auto element=(~rhs).begin(j); element!=(~rhs).end(j); ++element )
2945  v_[element->index()*nn_+j] -= element->value();
2946 }
2947 //*************************************************************************************************
2948 
2949 
2950 //*************************************************************************************************
2961 template< typename Type // Data type of the matrix
2962  , bool SO > // Storage order
2963 template< typename MT > // Type of the right-hand side dense matrix
2966 {
2967  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
2968  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
2969 
2970  const size_t jpos( n_ & size_t(-2) );
2971  BLAZE_INTERNAL_ASSERT( ( n_ - ( n_ % 2UL ) ) == jpos, "Invalid end calculation" );
2972 
2973  for( size_t i=0UL; i<m_; ++i ) {
2974  for( size_t j=0UL; j<jpos; j+=2UL ) {
2975  v_[i*nn_+j ] *= (~rhs)(i,j );
2976  v_[i*nn_+j+1UL] *= (~rhs)(i,j+1UL);
2977  }
2978  if( jpos < n_ ) {
2979  v_[i*nn_+jpos] *= (~rhs)(i,jpos);
2980  }
2981  }
2982 }
2983 //*************************************************************************************************
2984 
2985 
2986 //*************************************************************************************************
2997 template< typename Type // Data type of the matrix
2998  , bool SO > // Storage order
2999 template< typename MT > // Type of the right-hand side dense matrix
3002 {
3004 
3005  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
3006  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
3007 
3008  constexpr bool remainder( !usePadding || !IsPadded_v<MT> );
3009 
3010  for( size_t i=0UL; i<m_; ++i )
3011  {
3012  const size_t jpos( ( remainder )?( n_ & size_t(-SIMDSIZE) ):( n_ ) );
3013  BLAZE_INTERNAL_ASSERT( !remainder || ( n_ - ( n_ % (SIMDSIZE) ) ) == jpos, "Invalid end calculation" );
3014 
3015  size_t j( 0UL );
3016  Iterator left( begin(i) );
3017  ConstIterator_t<MT> right( (~rhs).begin(i) );
3018 
3019  for( ; (j+SIMDSIZE*3UL) < jpos; j+=SIMDSIZE*4UL ) {
3020  left.store( left.load() * right.load() ); left += SIMDSIZE; right += SIMDSIZE;
3021  left.store( left.load() * right.load() ); left += SIMDSIZE; right += SIMDSIZE;
3022  left.store( left.load() * right.load() ); left += SIMDSIZE; right += SIMDSIZE;
3023  left.store( left.load() * right.load() ); left += SIMDSIZE; right += SIMDSIZE;
3024  }
3025  for( ; j<jpos; j+=SIMDSIZE ) {
3026  left.store( left.load() * right.load() ); left += SIMDSIZE; right += SIMDSIZE;
3027  }
3028  for( ; remainder && j<n_; ++j ) {
3029  *left *= *right; ++left; ++right;
3030  }
3031  }
3032 }
3033 //*************************************************************************************************
3034 
3035 
3036 //*************************************************************************************************
3047 template< typename Type // Data type of the matrix
3048  , bool SO > // Storage order
3049 template< typename MT > // Type of the right-hand side dense matrix
3051 {
3053 
3054  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
3055  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
3056 
3057  constexpr size_t block( BLOCK_SIZE );
3058 
3059  for( size_t ii=0UL; ii<m_; ii+=block ) {
3060  const size_t iend( min( m_, ii+block ) );
3061  for( size_t jj=0UL; jj<n_; jj+=block ) {
3062  const size_t jend( min( n_, jj+block ) );
3063  for( size_t i=ii; i<iend; ++i ) {
3064  for( size_t j=jj; j<jend; ++j ) {
3065  v_[i*nn_+j] *= (~rhs)(i,j);
3066  }
3067  }
3068  }
3069  }
3070 }
3071 //*************************************************************************************************
3072 
3073 
3074 //*************************************************************************************************
3085 template< typename Type // Data type of the matrix
3086  , bool SO > // Storage order
3087 template< typename MT > // Type of the right-hand side sparse matrix
3089 {
3090  using blaze::reset;
3091 
3092  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
3093  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
3094 
3095  for( size_t i=0UL; i<m_; ++i )
3096  {
3097  size_t j( 0UL );
3098 
3099  for( auto element=(~rhs).begin(i); element!=(~rhs).end(i); ++element ) {
3100  for( ; j<element->index(); ++j )
3101  reset( v_[i*nn_+j] );
3102  v_[i*nn_+j] *= element->value();
3103  ++j;
3104  }
3105 
3106  for( ; j<n_; ++j ) {
3107  reset( v_[i*nn_+j] );
3108  }
3109  }
3110 }
3111 //*************************************************************************************************
3112 
3113 
3114 //*************************************************************************************************
3125 template< typename Type // Data type of the matrix
3126  , bool SO > // Storage order
3127 template< typename MT > // Type of the right-hand side sparse matrix
3129 {
3130  using blaze::reset;
3131 
3133 
3134  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
3135  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
3136 
3137  for( size_t j=0UL; j<n_; ++j )
3138  {
3139  size_t i( 0UL );
3140 
3141  for( auto element=(~rhs).begin(j); element!=(~rhs).end(j); ++element ) {
3142  for( ; i<element->index(); ++i )
3143  reset( v_[i*nn_+j] );
3144  v_[i*nn_+j] *= element->value();
3145  ++i;
3146  }
3147 
3148  for( ; i<m_; ++i ) {
3149  reset( v_[i*nn_+j] );
3150  }
3151  }
3152 }
3153 //*************************************************************************************************
3154 
3155 
3156 
3157 
3158 
3159 
3160 
3161 
3162 //=================================================================================================
3163 //
3164 // CLASS TEMPLATE SPECIALIZATION FOR COLUMN-MAJOR MATRICES
3165 //
3166 //=================================================================================================
3167 
3168 //*************************************************************************************************
3176 template< typename Type > // Data type of the matrix
3177 class DynamicMatrix<Type,true>
3178  : public DenseMatrix< DynamicMatrix<Type,true>, true >
3179 {
3180  public:
3181  //**Type definitions****************************************************************************
3182  using This = DynamicMatrix<Type,true>;
3184  using ResultType = This;
3187  using ElementType = Type;
3189  using ReturnType = const Type&;
3190  using CompositeType = const This&;
3191 
3192  using Reference = Type&;
3193  using ConstReference = const Type&;
3194  using Pointer = Type*;
3195  using ConstPointer = const Type*;
3196 
3199  //**********************************************************************************************
3200 
3201  //**Rebind struct definition********************************************************************
3204  template< typename NewType > // Data type of the other matrix
3205  struct Rebind {
3207  };
3208  //**********************************************************************************************
3209 
3210  //**Resize struct definition********************************************************************
3213  template< size_t NewM // Number of rows of the other matrix
3214  , size_t NewN > // Number of columns of the other matrix
3215  struct Resize {
3216  using Other = DynamicMatrix<Type,true>;
3217  };
3218  //**********************************************************************************************
3219 
3220  //**Compilation flags***************************************************************************
3222 
3226  static constexpr bool simdEnabled = IsVectorizable_v<Type>;
3227 
3229 
3232  static constexpr bool smpAssignable = !IsSMPAssignable_v<Type>;
3233  //**********************************************************************************************
3234 
3235  //**Constructors********************************************************************************
3238  explicit inline DynamicMatrix() noexcept;
3239  explicit inline DynamicMatrix( size_t m, size_t n );
3240  explicit inline DynamicMatrix( size_t m, size_t n, const Type& init );
3241  explicit inline DynamicMatrix( initializer_list< initializer_list<Type> > list );
3242 
3243  template< typename Other > explicit inline DynamicMatrix( size_t m, size_t n, const Other* array );
3244 
3245  template< typename Other, size_t Rows, size_t Cols >
3246  explicit inline DynamicMatrix( const Other (&array)[Rows][Cols] );
3247 
3248  inline DynamicMatrix( const DynamicMatrix& m );
3249  inline DynamicMatrix( DynamicMatrix&& m );
3250  template< typename MT, bool SO > inline DynamicMatrix( const Matrix<MT,SO>& m );
3252  //**********************************************************************************************
3253 
3254  //**Destructor**********************************************************************************
3257  inline ~DynamicMatrix();
3259  //**********************************************************************************************
3260 
3261  //**Data access functions***********************************************************************
3264  inline Reference operator()( size_t i, size_t j ) noexcept;
3265  inline ConstReference operator()( size_t i, size_t j ) const noexcept;
3266  inline Reference at( size_t i, size_t j );
3267  inline ConstReference at( size_t i, size_t j ) const;
3268  inline Pointer data () noexcept;
3269  inline ConstPointer data () const noexcept;
3270  inline Pointer data ( size_t j ) noexcept;
3271  inline ConstPointer data ( size_t j ) const noexcept;
3272  inline Iterator begin ( size_t j ) noexcept;
3273  inline ConstIterator begin ( size_t j ) const noexcept;
3274  inline ConstIterator cbegin( size_t j ) const noexcept;
3275  inline Iterator end ( size_t j ) noexcept;
3276  inline ConstIterator end ( size_t j ) const noexcept;
3277  inline ConstIterator cend ( size_t j ) const noexcept;
3279  //**********************************************************************************************
3280 
3281  //**Assignment operators************************************************************************
3284  inline DynamicMatrix& operator=( const Type& rhs );
3285  inline DynamicMatrix& operator=( initializer_list< initializer_list<Type> > list );
3286 
3287  template< typename Other, size_t Rows, size_t Cols >
3288  inline DynamicMatrix& operator=( const Other (&array)[Rows][Cols] );
3289 
3290  inline DynamicMatrix& operator=( const DynamicMatrix& rhs );
3291  inline DynamicMatrix& operator=( DynamicMatrix&& rhs );
3292 
3293  template< typename MT, bool SO > inline DynamicMatrix& operator= ( const Matrix<MT,SO>& rhs );
3294  template< typename MT, bool SO > inline DynamicMatrix& operator+=( const Matrix<MT,SO>& rhs );
3295  template< typename MT, bool SO > inline DynamicMatrix& operator-=( const Matrix<MT,SO>& rhs );
3296  template< typename MT, bool SO > inline DynamicMatrix& operator%=( const Matrix<MT,SO>& rhs );
3298  //**********************************************************************************************
3299 
3300  //**Utility functions***************************************************************************
3303  inline size_t rows() const noexcept;
3304  inline size_t columns() const noexcept;
3305  inline size_t spacing() const noexcept;
3306  inline size_t capacity() const noexcept;
3307  inline size_t capacity( size_t j ) const noexcept;
3308  inline size_t nonZeros() const;
3309  inline size_t nonZeros( size_t j ) const;
3310  inline void reset();
3311  inline void reset( size_t j );
3312  inline void clear();
3313  void resize ( size_t m, size_t n, bool preserve=true );
3314  inline void extend ( size_t m, size_t n, bool preserve=true );
3315  inline void reserve( size_t elements );
3316  inline void shrinkToFit();
3317  inline void swap( DynamicMatrix& m ) noexcept;
3319  //**********************************************************************************************
3320 
3321  //**Numeric functions***************************************************************************
3324  inline DynamicMatrix& transpose();
3325  inline DynamicMatrix& ctranspose();
3326 
3327  template< typename Other > inline DynamicMatrix& scale( const Other& scalar );
3329  //**********************************************************************************************
3330 
3331  private:
3332  //**********************************************************************************************
3334  template< typename MT >
3335  static constexpr bool VectorizedAssign_v =
3336  ( useOptimizedKernels &&
3337  simdEnabled && MT::simdEnabled &&
3338  IsSIMDCombinable_v< Type, ElementType_t<MT> > );
3339  //**********************************************************************************************
3340 
3341  //**********************************************************************************************
3343  template< typename MT >
3344  static constexpr bool VectorizedAddAssign_v =
3345  ( useOptimizedKernels &&
3346  simdEnabled && MT::simdEnabled &&
3347  IsSIMDCombinable_v< Type, ElementType_t<MT> > &&
3348  HasSIMDAdd_v< Type, ElementType_t<MT> > &&
3349  !IsDiagonal_v<MT> );
3350  //**********************************************************************************************
3351 
3352  //**********************************************************************************************
3354  template< typename MT >
3355  static constexpr bool VectorizedSubAssign_v =
3356  ( useOptimizedKernels &&
3357  simdEnabled && MT::simdEnabled &&
3358  IsSIMDCombinable_v< Type, ElementType_t<MT> > &&
3359  HasSIMDSub_v< Type, ElementType_t<MT> > &&
3360  !IsDiagonal_v<MT> );
3361  //**********************************************************************************************
3362 
3363  //**********************************************************************************************
3365  template< typename MT >
3366  static constexpr bool VectorizedSchurAssign_v =
3367  ( useOptimizedKernels &&
3368  simdEnabled && MT::simdEnabled &&
3369  IsSIMDCombinable_v< Type, ElementType_t<MT> > &&
3370  HasSIMDMult_v< Type, ElementType_t<MT> > );
3371  //**********************************************************************************************
3372 
3373  //**********************************************************************************************
3375  static constexpr size_t SIMDSIZE = SIMDTrait<ElementType>::size;
3376  //**********************************************************************************************
3377 
3378  public:
3379  //**Debugging functions*************************************************************************
3382  inline bool isIntact() const noexcept;
3384  //**********************************************************************************************
3385 
3386  //**Expression template evaluation functions****************************************************
3389  template< typename Other > inline bool canAlias ( const Other* alias ) const noexcept;
3390  template< typename Other > inline bool isAliased( const Other* alias ) const noexcept;
3391 
3392  inline bool isAligned () const noexcept;
3393  inline bool canSMPAssign() const noexcept;
3394 
3395  BLAZE_ALWAYS_INLINE SIMDType load ( size_t i, size_t j ) const noexcept;
3396  BLAZE_ALWAYS_INLINE SIMDType loada( size_t i, size_t j ) const noexcept;
3397  BLAZE_ALWAYS_INLINE SIMDType loadu( size_t i, size_t j ) const noexcept;
3398 
3399  BLAZE_ALWAYS_INLINE void store ( size_t i, size_t j, const SIMDType& value ) noexcept;
3400  BLAZE_ALWAYS_INLINE void storea( size_t i, size_t j, const SIMDType& value ) noexcept;
3401  BLAZE_ALWAYS_INLINE void storeu( size_t i, size_t j, const SIMDType& value ) noexcept;
3402  BLAZE_ALWAYS_INLINE void stream( size_t i, size_t j, const SIMDType& value ) noexcept;
3403 
3404  template< typename MT >
3405  inline auto assign( const DenseMatrix<MT,true>& rhs ) -> DisableIf_t< VectorizedAssign_v<MT> >;
3406 
3407  template< typename MT >
3408  inline auto assign( const DenseMatrix<MT,true>& rhs ) -> EnableIf_t< VectorizedAssign_v<MT> >;
3409 
3410  template< typename MT > inline void assign( const DenseMatrix<MT,false>& rhs );
3411  template< typename MT > inline void assign( const SparseMatrix<MT,true>& rhs );
3412  template< typename MT > inline void assign( const SparseMatrix<MT,false>& rhs );
3413 
3414  template< typename MT >
3415  inline auto addAssign( const DenseMatrix<MT,true>& rhs ) -> DisableIf_t< VectorizedAddAssign_v<MT> >;
3416 
3417  template< typename MT >
3418  inline auto addAssign( const DenseMatrix<MT,true>& rhs ) -> EnableIf_t< VectorizedAddAssign_v<MT> >;
3419 
3420  template< typename MT > inline void addAssign( const DenseMatrix<MT,false>& rhs );
3421  template< typename MT > inline void addAssign( const SparseMatrix<MT,true>& rhs );
3422  template< typename MT > inline void addAssign( const SparseMatrix<MT,false>& rhs );
3423 
3424  template< typename MT >
3425  inline auto subAssign ( const DenseMatrix<MT,true>& rhs ) -> DisableIf_t< VectorizedSubAssign_v<MT> >;
3426 
3427  template< typename MT >
3428  inline auto subAssign ( const DenseMatrix<MT,true>& rhs ) -> EnableIf_t< VectorizedSubAssign_v<MT> >;
3429 
3430  template< typename MT > inline void subAssign( const DenseMatrix<MT,false>& rhs );
3431  template< typename MT > inline void subAssign( const SparseMatrix<MT,true>& rhs );
3432  template< typename MT > inline void subAssign( const SparseMatrix<MT,false>& rhs );
3433 
3434  template< typename MT >
3435  inline auto schurAssign ( const DenseMatrix<MT,true>& rhs ) -> DisableIf_t< VectorizedSchurAssign_v<MT> >;
3436 
3437  template< typename MT >
3438  inline auto schurAssign ( const DenseMatrix<MT,true>& rhs ) -> EnableIf_t< VectorizedSchurAssign_v<MT> >;
3439 
3440  template< typename MT > inline void schurAssign( const DenseMatrix<MT,false>& rhs );
3441  template< typename MT > inline void schurAssign( const SparseMatrix<MT,true>& rhs );
3442  template< typename MT > inline void schurAssign( const SparseMatrix<MT,false>& rhs );
3444  //**********************************************************************************************
3445 
3446  private:
3447  //**Utility functions***************************************************************************
3450  inline size_t addPadding( size_t minRows ) const noexcept;
3452  //**********************************************************************************************
3453 
3454  //**Member variables****************************************************************************
3457  size_t m_;
3458  size_t mm_;
3459  size_t n_;
3460  size_t capacity_;
3461  Type* BLAZE_RESTRICT v_;
3462 
3465  //**********************************************************************************************
3466 
3467  //**Compile time checks*************************************************************************
3472  //**********************************************************************************************
3473 };
3475 //*************************************************************************************************
3476 
3477 
3478 
3479 
3480 //=================================================================================================
3481 //
3482 // CONSTRUCTORS
3483 //
3484 //=================================================================================================
3485 
3486 //*************************************************************************************************
3490 template< typename Type > // Data type of the matrix
3491 inline DynamicMatrix<Type,true>::DynamicMatrix() noexcept
3492  : m_ ( 0UL ) // The current number of rows of the matrix
3493  , mm_ ( 0UL ) // The alignment adjusted number of rows
3494  , n_ ( 0UL ) // The current number of columns of the matrix
3495  , capacity_( 0UL ) // The maximum capacity of the matrix
3496  , v_ ( nullptr ) // The matrix elements
3497 {}
3499 //*************************************************************************************************
3500 
3501 
3502 //*************************************************************************************************
3512 template< typename Type > // Data type of the matrix
3513 inline DynamicMatrix<Type,true>::DynamicMatrix( size_t m, size_t n )
3514  : m_ ( m ) // The current number of rows of the matrix
3515  , mm_ ( addPadding( m ) ) // The alignment adjusted number of rows
3516  , n_ ( n ) // The current number of columns of the matrix
3517  , capacity_( mm_*n_ ) // The maximum capacity of the matrix
3518  , v_ ( allocate<Type>( capacity_ ) ) // The matrix elements
3519 {
3520  if( IsVectorizable_v<Type> ) {
3521  for( size_t j=0UL; j<n_; ++j ) {
3522  for( size_t i=m_; i<mm_; ++i ) {
3523  v_[i+j*mm_] = Type();
3524  }
3525  }
3526  }
3527 
3528  BLAZE_INTERNAL_ASSERT( isIntact(), "Invariant violation detected" );
3529 }
3531 //*************************************************************************************************
3532 
3533 
3534 //*************************************************************************************************
3544 template< typename Type > // Data type of the matrix
3545 inline DynamicMatrix<Type,true>::DynamicMatrix( size_t m, size_t n, const Type& init )
3546  : DynamicMatrix( m, n )
3547 {
3548  for( size_t j=0UL; j<n_; ++j ) {
3549  for( size_t i=0UL; i<m_; ++i ) {
3550  v_[i+j*mm_] = init;
3551  }
3552  }
3553 
3554  BLAZE_INTERNAL_ASSERT( isIntact(), "Invariant violation detected" );
3555 }
3557 //*************************************************************************************************
3558 
3559 
3560 //*************************************************************************************************
3581 template< typename Type > // Data type of the matrix
3582 inline DynamicMatrix<Type,true>::DynamicMatrix( initializer_list< initializer_list<Type> > list )
3583  : DynamicMatrix( list.size(), determineColumns( list ) )
3584 {
3585  size_t i( 0UL );
3586 
3587  for( const auto& rowList : list ) {
3588  size_t j( 0UL );
3589  for( const auto& element : rowList ) {
3590  v_[i+j*mm_] = element;
3591  ++j;
3592  }
3593  for( ; j<n_; ++j ) {
3594  v_[i+j*mm_] = Type();
3595  }
3596  ++i;
3597  }
3598 
3599  BLAZE_INTERNAL_ASSERT( i == m_, "Invalid number of elements detected" );
3600  BLAZE_INTERNAL_ASSERT( isIntact(), "Invariant violation detected" );
3601 }
3603 //*************************************************************************************************
3604 
3605 
3606 //*************************************************************************************************
3630 template< typename Type > // Data type of the matrix
3631 template< typename Other > // Data type of the initialization array
3632 inline DynamicMatrix<Type,true>::DynamicMatrix( size_t m, size_t n, const Other* array )
3633  : DynamicMatrix( m, n )
3634 {
3635  for( size_t j=0UL; j<n; ++j ) {
3636  for( size_t i=0UL; i<m; ++i ) {
3637  v_[i+j*mm_] = array[i+j*m];
3638  }
3639  }
3640 
3641  BLAZE_INTERNAL_ASSERT( isIntact(), "Invariant violation detected" );
3642 }
3644 //*************************************************************************************************
3645 
3646 
3647 //*************************************************************************************************
3669 template< typename Type > // Data type of the matrix
3670 template< typename Other // Data type of the initialization array
3671  , size_t Rows // Number of rows of the initialization array
3672  , size_t Cols > // Number of columns of the initialization array
3673 inline DynamicMatrix<Type,true>::DynamicMatrix( const Other (&array)[Rows][Cols] )
3674  : DynamicMatrix( Rows, Cols )
3675 {
3676  for( size_t j=0UL; j<Cols; ++j ) {
3677  for( size_t i=0UL; i<Rows; ++i ) {
3678  v_[i+j*mm_] = array[i][j];
3679  }
3680  }
3681 
3682  BLAZE_INTERNAL_ASSERT( isIntact(), "Invariant violation detected" );
3683 }
3685 //*************************************************************************************************
3686 
3687 
3688 //*************************************************************************************************
3697 template< typename Type > // Data type of the matrix
3698 inline DynamicMatrix<Type,true>::DynamicMatrix( const DynamicMatrix& m )
3699  : DynamicMatrix( m.m_, m.n_ )
3700 {
3701  BLAZE_INTERNAL_ASSERT( capacity_ <= m.capacity_, "Invalid capacity estimation" );
3702 
3703  smpAssign( *this, m );
3704 
3705  BLAZE_INTERNAL_ASSERT( isIntact(), "Invariant violation detected" );
3706 }
3708 //*************************************************************************************************
3709 
3710 
3711 //*************************************************************************************************
3717 template< typename Type > // Data type of the matrix
3718 inline DynamicMatrix<Type,true>::DynamicMatrix( DynamicMatrix&& m )
3719  : m_ ( m.m_ ) // The current number of rows of the matrix
3720  , mm_ ( m.mm_ ) // The alignment adjusted number of rows
3721  , n_ ( m.n_ ) // The current number of columns of the matrix
3722  , capacity_( m.capacity_ ) // The maximum capacity of the matrix
3723  , v_ ( m.v_ ) // The matrix elements
3724 {
3725  m.m_ = 0UL;
3726  m.mm_ = 0UL;
3727  m.n_ = 0UL;
3728  m.capacity_ = 0UL;
3729  m.v_ = nullptr;
3730 }
3732 //*************************************************************************************************
3733 
3734 
3735 //*************************************************************************************************
3741 template< typename Type > // Data type of the matrix
3742 template< typename MT // Type of the foreign matrix
3743  , bool SO > // Storage order of the foreign matrix
3744 inline DynamicMatrix<Type,true>::DynamicMatrix( const Matrix<MT,SO>& m )
3745  : DynamicMatrix( (~m).rows(), (~m).columns() )
3746 {
3747  if( IsSparseMatrix_v<MT> ) {
3748  reset();
3749  }
3750 
3751  smpAssign( *this, ~m );
3752 
3753  BLAZE_INTERNAL_ASSERT( isIntact(), "Invariant violation detected" );
3754 }
3756 //*************************************************************************************************
3757 
3758 
3759 
3760 
3761 //=================================================================================================
3762 //
3763 // DESTRUCTOR
3764 //
3765 //=================================================================================================
3766 
3767 //*************************************************************************************************
3771 template< typename Type > // Data type of the matrix
3773 {
3774  deallocate( v_ );
3775 }
3777 //*************************************************************************************************
3778 
3779 
3780 
3781 
3782 //=================================================================================================
3783 //
3784 // DATA ACCESS FUNCTIONS
3785 //
3786 //=================================================================================================
3787 
3788 //*************************************************************************************************
3799 template< typename Type > // Data type of the matrix
3801  DynamicMatrix<Type,true>::operator()( size_t i, size_t j ) noexcept
3802 {
3803  BLAZE_USER_ASSERT( i<m_, "Invalid row access index" );
3804  BLAZE_USER_ASSERT( j<n_, "Invalid column access index" );
3805  return v_[i+j*mm_];
3806 }
3808 //*************************************************************************************************
3809 
3810 
3811 //*************************************************************************************************
3822 template< typename Type > // Data type of the matrix
3824  DynamicMatrix<Type,true>::operator()( size_t i, size_t j ) const noexcept
3825 {
3826  BLAZE_USER_ASSERT( i<m_, "Invalid row access index" );
3827  BLAZE_USER_ASSERT( j<n_, "Invalid column access index" );
3828  return v_[i+j*mm_];
3829 }
3831 //*************************************************************************************************
3832 
3833 
3834 //*************************************************************************************************
3846 template< typename Type > // Data type of the matrix
3848  DynamicMatrix<Type,true>::at( size_t i, size_t j )
3849 {
3850  if( i >= m_ ) {
3851  BLAZE_THROW_OUT_OF_RANGE( "Invalid row access index" );
3852  }
3853  if( j >= n_ ) {
3854  BLAZE_THROW_OUT_OF_RANGE( "Invalid column access index" );
3855  }
3856  return (*this)(i,j);
3857 }
3859 //*************************************************************************************************
3860 
3861 
3862 //*************************************************************************************************
3874 template< typename Type > // Data type of the matrix
3876  DynamicMatrix<Type,true>::at( size_t i, size_t j ) const
3877 {
3878  if( i >= m_ ) {
3879  BLAZE_THROW_OUT_OF_RANGE( "Invalid row access index" );
3880  }
3881  if( j >= n_ ) {
3882  BLAZE_THROW_OUT_OF_RANGE( "Invalid column access index" );
3883  }
3884  return (*this)(i,j);
3885 }
3887 //*************************************************************************************************
3888 
3889 
3890 //*************************************************************************************************
3902 template< typename Type > // Data type of the matrix
3903 inline typename DynamicMatrix<Type,true>::Pointer
3905 {
3906  return v_;
3907 }
3909 //*************************************************************************************************
3910 
3911 
3912 //*************************************************************************************************
3924 template< typename Type > // Data type of the matrix
3926  DynamicMatrix<Type,true>::data() const noexcept
3927 {
3928  return v_;
3929 }
3931 //*************************************************************************************************
3932 
3933 
3934 //*************************************************************************************************
3943 template< typename Type > // Data type of the matrix
3944 inline typename DynamicMatrix<Type,true>::Pointer
3945  DynamicMatrix<Type,true>::data( size_t j ) noexcept
3946 {
3947  BLAZE_USER_ASSERT( j < n_, "Invalid dense matrix column access index" );
3948  return v_ + j*mm_;
3949 }
3951 //*************************************************************************************************
3952 
3953 
3954 //*************************************************************************************************
3963 template< typename Type > // Data type of the matrix
3965  DynamicMatrix<Type,true>::data( size_t j ) const noexcept
3966 {
3967  BLAZE_USER_ASSERT( j < n_, "Invalid dense matrix column access index" );
3968  return v_ + j*mm_;
3969 }
3971 //*************************************************************************************************
3972 
3973 
3974 //*************************************************************************************************
3981 template< typename Type > // Data type of the matrix
3982 inline typename DynamicMatrix<Type,true>::Iterator
3983  DynamicMatrix<Type,true>::begin( size_t j ) noexcept
3984 {
3985  BLAZE_USER_ASSERT( j < n_, "Invalid dense matrix column access index" );
3986  return Iterator( v_ + j*mm_ );
3987 }
3989 //*************************************************************************************************
3990 
3991 
3992 //*************************************************************************************************
3999 template< typename Type > // Data type of the matrix
4001  DynamicMatrix<Type,true>::begin( size_t j ) const noexcept
4002 {
4003  BLAZE_USER_ASSERT( j < n_, "Invalid dense matrix column access index" );
4004  return ConstIterator( v_ + j*mm_ );
4005 }
4007 //*************************************************************************************************
4008 
4009 
4010 //*************************************************************************************************
4017 template< typename Type > // Data type of the matrix
4019  DynamicMatrix<Type,true>::cbegin( size_t j ) const noexcept
4020 {
4021  BLAZE_USER_ASSERT( j < n_, "Invalid dense matrix column access index" );
4022  return ConstIterator( v_ + j*mm_ );
4023 }
4025 //*************************************************************************************************
4026 
4027 
4028 //*************************************************************************************************
4035 template< typename Type > // Data type of the matrix
4036 inline typename DynamicMatrix<Type,true>::Iterator
4037  DynamicMatrix<Type,true>::end( size_t j ) noexcept
4038 {
4039  BLAZE_USER_ASSERT( j < n_, "Invalid dense matrix column access index" );
4040  return Iterator( v_ + j*mm_ + m_ );
4041 }
4043 //*************************************************************************************************
4044 
4045 
4046 //*************************************************************************************************
4053 template< typename Type > // Data type of the matrix
4055  DynamicMatrix<Type,true>::end( size_t j ) const noexcept
4056 {
4057  BLAZE_USER_ASSERT( j < n_, "Invalid dense matrix column access index" );
4058  return ConstIterator( v_ + j*mm_ + m_ );
4059 }
4061 //*************************************************************************************************
4062 
4063 
4064 //*************************************************************************************************
4071 template< typename Type > // Data type of the matrix
4073  DynamicMatrix<Type,true>::cend( size_t j ) const noexcept
4074 {
4075  BLAZE_USER_ASSERT( j < n_, "Invalid dense matrix column access index" );
4076  return ConstIterator( v_ + j*mm_ + m_ );
4077 }
4079 //*************************************************************************************************
4080 
4081 
4082 
4083 
4084 //=================================================================================================
4085 //
4086 // ASSIGNMENT OPERATORS
4087 //
4088 //=================================================================================================
4089 
4090 //*************************************************************************************************
4097 template< typename Type > // Data type of the matrix
4098 inline DynamicMatrix<Type,true>& DynamicMatrix<Type,true>::operator=( const Type& rhs )
4099 {
4100  for( size_t j=0UL; j<n_; ++j )
4101  for( size_t i=0UL; i<m_; ++i )
4102  v_[i+j*mm_] = rhs;
4103 
4104  return *this;
4105 }
4107 //*************************************************************************************************
4108 
4109 
4110 //*************************************************************************************************
4132 template< typename Type > // Data type of the matrix
4133 inline DynamicMatrix<Type,true>&
4134  DynamicMatrix<Type,true>::operator=( initializer_list< initializer_list<Type> > list )
4135 {
4136  resize( list.size(), determineColumns( list ), false );
4137 
4138  size_t i( 0UL );
4139 
4140  for( const auto& rowList : list ) {
4141  size_t j( 0UL );
4142  for( const auto& element : rowList ) {
4143  v_[i+j*mm_] = element;
4144  ++j;
4145  }
4146  for( ; j<n_; ++j ) {
4147  v_[i+j*mm_] = Type();
4148  }
4149  ++i;
4150  }
4151 
4152  return *this;
4153 }
4155 //*************************************************************************************************
4156 
4157 
4158 //*************************************************************************************************
4180 template< typename Type > // Data type of the matrix
4181 template< typename Other // Data type of the initialization array
4182  , size_t Rows // Number of rows of the initialization array
4183  , size_t Cols > // Number of columns of the initialization array
4184 inline DynamicMatrix<Type,true>& DynamicMatrix<Type,true>::operator=( const Other (&array)[Rows][Cols] )
4185 {
4186  resize( Rows, Cols, false );
4187 
4188  for( size_t j=0UL; j<Cols; ++j )
4189  for( size_t i=0UL; i<Rows; ++i )
4190  v_[i+j*mm_] = array[i][j];
4191 
4192  return *this;
4193 }
4195 //*************************************************************************************************
4196 
4197 
4198 //*************************************************************************************************
4208 template< typename Type > // Data type of the matrix
4209 inline DynamicMatrix<Type,true>& DynamicMatrix<Type,true>::operator=( const DynamicMatrix& rhs )
4210 {
4211  if( &rhs == this ) return *this;
4212 
4213  resize( rhs.m_, rhs.n_, false );
4214  smpAssign( *this, ~rhs );
4215 
4216  BLAZE_INTERNAL_ASSERT( isIntact(), "Invariant violation detected" );
4217 
4218  return *this;
4219 }
4221 //*************************************************************************************************
4222 
4223 
4224 //*************************************************************************************************
4231 template< typename Type > // Data type of the matrix
4232 inline DynamicMatrix<Type,true>& DynamicMatrix<Type,true>::operator=( DynamicMatrix&& rhs )
4233 {
4234  deallocate( v_ );
4235 
4236  m_ = rhs.m_;
4237  mm_ = rhs.mm_;
4238  n_ = rhs.n_;
4239  capacity_ = rhs.capacity_;
4240  v_ = rhs.v_;
4241 
4242  rhs.m_ = 0UL;
4243  rhs.mm_ = 0UL;
4244  rhs.n_ = 0UL;
4245  rhs.capacity_ = 0UL;
4246  rhs.v_ = nullptr;
4247 
4248  return *this;
4249 }
4251 //*************************************************************************************************
4252 
4253 
4254 //*************************************************************************************************
4264 template< typename Type > // Data type of the matrix
4265 template< typename MT // Type of the right-hand side matrix
4266  , bool SO > // Storage order of the right-hand side matrix
4267 inline DynamicMatrix<Type,true>& DynamicMatrix<Type,true>::operator=( const Matrix<MT,SO>& rhs )
4268 {
4269  using TT = decltype( trans( *this ) );
4270  using CT = decltype( ctrans( *this ) );
4271  using IT = decltype( inv( *this ) );
4272 
4273  if( IsSame_v<MT,TT> && (~rhs).isAliased( this ) ) {
4274  transpose();
4275  }
4276  else if( IsSame_v<MT,CT> && (~rhs).isAliased( this ) ) {
4277  ctranspose();
4278  }
4279  else if( !IsSame_v<MT,IT> && (~rhs).canAlias( this ) ) {
4280  DynamicMatrix tmp( ~rhs );
4281  swap( tmp );
4282  }
4283  else {
4284  resize( (~rhs).rows(), (~rhs).columns(), false );
4285  if( IsSparseMatrix_v<MT> )
4286  reset();
4287  smpAssign( *this, ~rhs );
4288  }
4289 
4290  BLAZE_INTERNAL_ASSERT( isIntact(), "Invariant violation detected" );
4291 
4292  return *this;
4293 }
4295 //*************************************************************************************************
4296 
4297 
4298 //*************************************************************************************************
4309 template< typename Type > // Data type of the matrix
4310 template< typename MT // Type of the right-hand side matrix
4311  , bool SO > // Storage order of the right-hand side matrix
4312 inline DynamicMatrix<Type,true>& DynamicMatrix<Type,true>::operator+=( const Matrix<MT,SO>& rhs )
4313 {
4314  if( (~rhs).rows() != m_ || (~rhs).columns() != n_ ) {
4315  BLAZE_THROW_INVALID_ARGUMENT( "Matrix sizes do not match" );
4316  }
4317 
4318  if( (~rhs).canAlias( this ) ) {
4319  const ResultType_t<MT> tmp( ~rhs );
4320  smpAddAssign( *this, tmp );
4321  }
4322  else {
4323  smpAddAssign( *this, ~rhs );
4324  }
4325 
4326  BLAZE_INTERNAL_ASSERT( isIntact(), "Invariant violation detected" );
4327 
4328  return *this;
4329 }
4331 //*************************************************************************************************
4332 
4333 
4334 //*************************************************************************************************
4345 template< typename Type > // Data type of the matrix
4346 template< typename MT // Type of the right-hand side matrix
4347  , bool SO > // Storage order of the right-hand side matrix
4348 inline DynamicMatrix<Type,true>& DynamicMatrix<Type,true>::operator-=( const Matrix<MT,SO>& rhs )
4349 {
4350  if( (~rhs).rows() != m_ || (~rhs).columns() != n_ ) {
4351  BLAZE_THROW_INVALID_ARGUMENT( "Matrix sizes do not match" );
4352  }
4353 
4354  if( (~rhs).canAlias( this ) ) {
4355  const ResultType_t<MT> tmp( ~rhs );
4356  smpSubAssign( *this, tmp );
4357  }
4358  else {
4359  smpSubAssign( *this, ~rhs );
4360  }
4361 
4362  BLAZE_INTERNAL_ASSERT( isIntact(), "Invariant violation detected" );
4363 
4364  return *this;
4365 }
4367 //*************************************************************************************************
4368 
4369 
4370 //*************************************************************************************************
4381 template< typename Type > // Data type of the matrix
4382 template< typename MT // Type of the right-hand side matrix
4383  , bool SO > // Storage order of the right-hand side matrix
4384 inline DynamicMatrix<Type,true>& DynamicMatrix<Type,true>::operator%=( const Matrix<MT,SO>& rhs )
4385 {
4386  if( (~rhs).rows() != m_ || (~rhs).columns() != n_ ) {
4387  BLAZE_THROW_INVALID_ARGUMENT( "Matrix sizes do not match" );
4388  }
4389 
4390  if( (~rhs).canAlias( this ) ) {
4391  const ResultType_t<MT> tmp( ~rhs );
4392  smpSchurAssign( *this, tmp );
4393  }
4394  else {
4395  smpSchurAssign( *this, ~rhs );
4396  }
4397 
4398  BLAZE_INTERNAL_ASSERT( isIntact(), "Invariant violation detected" );
4399 
4400  return *this;
4401 }
4403 //*************************************************************************************************
4404 
4405 
4406 
4407 
4408 //=================================================================================================
4409 //
4410 // UTILITY FUNCTIONS
4411 //
4412 //=================================================================================================
4413 
4414 //*************************************************************************************************
4420 template< typename Type > // Data type of the matrix
4421 inline size_t DynamicMatrix<Type,true>::rows() const noexcept
4422 {
4423  return m_;
4424 }
4426 //*************************************************************************************************
4427 
4428 
4429 //*************************************************************************************************
4435 template< typename Type > // Data type of the matrix
4436 inline size_t DynamicMatrix<Type,true>::columns() const noexcept
4437 {
4438  return n_;
4439 }
4441 //*************************************************************************************************
4442 
4443 
4444 //*************************************************************************************************
4453 template< typename Type > // Data type of the matrix
4454 inline size_t DynamicMatrix<Type,true>::spacing() const noexcept
4455 {
4456  return mm_;
4457 }
4459 //*************************************************************************************************
4460 
4461 
4462 //*************************************************************************************************
4468 template< typename Type > // Data type of the matrix
4469 inline size_t DynamicMatrix<Type,true>::capacity() const noexcept
4470 {
4471  return capacity_;
4472 }
4474 //*************************************************************************************************
4475 
4476 
4477 //*************************************************************************************************
4484 template< typename Type > // Data type of the matrix
4485 inline size_t DynamicMatrix<Type,true>::capacity( size_t j ) const noexcept
4486 {
4487  UNUSED_PARAMETER( j );
4488  BLAZE_USER_ASSERT( j < columns(), "Invalid column access index" );
4489  return mm_;
4490 }
4492 //*************************************************************************************************
4493 
4494 
4495 //*************************************************************************************************
4501 template< typename Type > // Data type of the matrix
4502 inline size_t DynamicMatrix<Type,true>::nonZeros() const
4503 {
4504  size_t nonzeros( 0UL );
4505 
4506  for( size_t j=0UL; j<n_; ++j )
4507  for( size_t i=0UL; i<m_; ++i )
4508  if( !isDefault( v_[i+j*mm_] ) )
4509  ++nonzeros;
4510 
4511  return nonzeros;
4512 }
4514 //*************************************************************************************************
4515 
4516 
4517 //*************************************************************************************************
4524 template< typename Type > // Data type of the matrix
4525 inline size_t DynamicMatrix<Type,true>::nonZeros( size_t j ) const
4526 {
4527  BLAZE_USER_ASSERT( j < columns(), "Invalid column access index" );
4528 
4529  const size_t iend( j*mm_ + m_ );
4530  size_t nonzeros( 0UL );
4531 
4532  for( size_t i=j*mm_; i<iend; ++i )
4533  if( !isDefault( v_[i] ) )
4534  ++nonzeros;
4535 
4536  return nonzeros;
4537 }
4539 //*************************************************************************************************
4540 
4541 
4542 //*************************************************************************************************
4548 template< typename Type > // Data type of the matrix
4549 inline void DynamicMatrix<Type,true>::reset()
4550 {
4551  using blaze::clear;
4552 
4553  for( size_t j=0UL; j<n_; ++j )
4554  for( size_t i=0UL; i<m_; ++i )
4555  clear( v_[i+j*mm_] );
4556 }
4558 //*************************************************************************************************
4559 
4560 
4561 //*************************************************************************************************
4571 template< typename Type > // Data type of the matrix
4572 inline void DynamicMatrix<Type,true>::reset( size_t j )
4573 {
4574  using blaze::clear;
4575 
4576  BLAZE_USER_ASSERT( j < columns(), "Invalid column access index" );
4577  for( size_t i=0UL; i<m_; ++i )
4578  clear( v_[i+j*mm_] );
4579 }
4581 //*************************************************************************************************
4582 
4583 
4584 //*************************************************************************************************
4592 template< typename Type > // Data type of the matrix
4593 inline void DynamicMatrix<Type,true>::clear()
4594 {
4595  resize( 0UL, 0UL, false );
4596 }
4598 //*************************************************************************************************
4599 
4600 
4601 //*************************************************************************************************
4636 template< typename Type > // Data type of the matrix
4637 void DynamicMatrix<Type,true>::resize( size_t m, size_t n, bool preserve )
4638 {
4639  using std::swap;
4640  using blaze::min;
4641 
4642  if( m == m_ && n == n_ ) return;
4643 
4644  const size_t mm( addPadding( m ) );
4645 
4646  if( preserve )
4647  {
4648  Type* BLAZE_RESTRICT v = allocate<Type>( mm*n );
4649  const size_t min_m( min( m, m_ ) );
4650  const size_t min_n( min( n, n_ ) );
4651 
4652  for( size_t j=0UL; j<min_n; ++j ) {
4653  transfer( v_+j*mm_, v_+min_m+j*mm_, v+j*mm );
4654  }
4655 
4656  swap( v_, v );
4657  deallocate( v );
4658  capacity_ = mm*n;
4659  }
4660  else if( mm*n > capacity_ ) {
4661  Type* BLAZE_RESTRICT v = allocate<Type>( mm*n );
4662  swap( v_, v );
4663  deallocate( v );
4664  capacity_ = mm*n;
4665  }
4666 
4667  if( IsVectorizable_v<Type> ) {
4668  for( size_t j=0UL; j<n; ++j )
4669  for( size_t i=m; i<mm; ++i )
4670  v_[i+j*mm] = Type();
4671  }
4672 
4673  m_ = m;
4674  mm_ = mm;
4675  n_ = n;
4676 }
4678 //*************************************************************************************************
4679 
4680 
4681 //*************************************************************************************************
4696 template< typename Type > // Data type of the matrix
4697 inline void DynamicMatrix<Type,true>::extend( size_t m, size_t n, bool preserve )
4698 {
4699  resize( m_+m, n_+n, preserve );
4700 }
4702 //*************************************************************************************************
4703 
4704 
4705 //*************************************************************************************************
4715 template< typename Type > // Data type of the matrix
4716 inline void DynamicMatrix<Type,true>::reserve( size_t elements )
4717 {
4718  using std::swap;
4719 
4720  if( elements > capacity_ )
4721  {
4722  // Allocating a new array
4723  Type* BLAZE_RESTRICT tmp = allocate<Type>( elements );
4724 
4725  // Initializing the new array
4726  transfer( v_, v_+capacity_, tmp );
4727 
4728  if( IsVectorizable_v<Type> ) {
4729  for( size_t i=capacity_; i<elements; ++i )
4730  tmp[i] = Type();
4731  }
4732 
4733  // Replacing the old array
4734  swap( tmp, v_ );
4735  deallocate( tmp );
4736  capacity_ = elements;
4737  }
4738 }
4740 //*************************************************************************************************
4741 
4742 
4743 //*************************************************************************************************
4754 template< typename Type > // Data type of the matrix
4756 {
4757  if( ( mm_ * n_ ) < capacity_ ) {
4758  DynamicMatrix( *this ).swap( *this );
4759  }
4760 }
4762 //*************************************************************************************************
4763 
4764 
4765 //*************************************************************************************************
4772 template< typename Type > // Data type of the matrix
4773 inline void DynamicMatrix<Type,true>::swap( DynamicMatrix& m ) noexcept
4774 {
4775  using std::swap;
4776 
4777  swap( m_ , m.m_ );
4778  swap( mm_, m.mm_ );
4779  swap( n_ , m.n_ );
4780  swap( capacity_, m.capacity_ );
4781  swap( v_ , m.v_ );
4782 }
4784 //*************************************************************************************************
4785 
4786 
4787 //*************************************************************************************************
4797 template< typename Type > // Data type of the matrix
4798 inline size_t DynamicMatrix<Type,true>::addPadding( size_t values ) const noexcept
4799 {
4800  if( usePadding && IsVectorizable_v<Type> )
4801  return nextMultiple<size_t>( values, SIMDSIZE );
4802  else return values;
4803 }
4805 //*************************************************************************************************
4806 
4807 
4808 
4809 
4810 //=================================================================================================
4811 //
4812 // NUMERIC FUNCTIONS
4813 //
4814 //=================================================================================================
4815 
4816 //*************************************************************************************************
4822 template< typename Type > // Data type of the matrix
4823 inline DynamicMatrix<Type,true>& DynamicMatrix<Type,true>::transpose()
4824 {
4825  using std::swap;
4826 
4827  constexpr size_t block( BLOCK_SIZE );
4828 
4829  if( m_ == n_ )
4830  {
4831  for( size_t jj=0UL; jj<n_; jj+=block ) {
4832  const size_t jend( min( jj+block, n_ ) );
4833  for( size_t ii=0UL; ii<=jj; ii+=block ) {
4834  for( size_t j=jj; j<jend; ++j ) {
4835  const size_t iend( min( ii+block, m_, j ) );
4836  for( size_t i=ii; i<iend; ++i ) {
4837  swap( v_[i+j*mm_], v_[j+i*mm_] );
4838  }
4839  }
4840  }
4841  }
4842  }
4843  else
4844  {
4845  DynamicMatrix tmp( trans(*this) );
4846  this->swap( tmp );
4847  }
4848 
4849  return *this;
4850 }
4852 //*************************************************************************************************
4853 
4854 
4855 //*************************************************************************************************
4861 template< typename Type > // Data type of the matrix
4862 inline DynamicMatrix<Type,true>& DynamicMatrix<Type,true>::ctranspose()
4863 {
4864  constexpr size_t block( BLOCK_SIZE );
4865 
4866  if( m_ == n_ )
4867  {
4868  for( size_t jj=0UL; jj<n_; jj+=block ) {
4869  const size_t jend( min( jj+block, n_ ) );
4870  for( size_t ii=0UL; ii<jj; ii+=block ) {
4871  const size_t iend( min( ii+block, m_ ) );
4872  for( size_t j=jj; j<jend; ++j ) {
4873  for( size_t i=ii; i<iend; ++i ) {
4874  cswap( v_[i+j*mm_], v_[j+i*mm_] );
4875  }
4876  }
4877  }
4878  for( size_t j=jj; j<jend; ++j ) {
4879  for( size_t i=jj; i<j; ++i ) {
4880  cswap( v_[i+j*mm_], v_[j+i*mm_] );
4881  }
4882  conjugate( v_[j+j*mm_] );
4883  }
4884  }
4885  }
4886  else
4887  {
4888  DynamicMatrix tmp( ctrans(*this) );
4889  this->swap( tmp );
4890  }
4891 
4892  return *this;
4893 }
4895 //*************************************************************************************************
4896 
4897 
4898 //*************************************************************************************************
4916 template< typename Type > // Data type of the matrix
4917 template< typename Other > // Data type of the scalar value
4918 inline DynamicMatrix<Type,true>& DynamicMatrix<Type,true>::scale( const Other& scalar )
4919 {
4920  for( size_t j=0UL; j<n_; ++j )
4921  for( size_t i=0UL; i<m_; ++i )
4922  v_[i+j*mm_] *= scalar;
4923 
4924  return *this;
4925 }
4927 //*************************************************************************************************
4928 
4929 
4930 
4931 
4932 //=================================================================================================
4933 //
4934 // DEBUGGING FUNCTIONS
4935 //
4936 //=================================================================================================
4937 
4938 //*************************************************************************************************
4948 template< typename Type > // Data type of the matrix
4949 inline bool DynamicMatrix<Type,true>::isIntact() const noexcept
4950 {
4951  if( m_ * n_ > capacity_ )
4952  return false;
4953 
4954  if( IsVectorizable_v<Type> ) {
4955  for( size_t j=0UL; j<n_; ++j ) {
4956  for( size_t i=m_; i<mm_; ++i ) {
4957  if( v_[i+j*mm_] != Type() )
4958  return false;
4959  }
4960  }
4961  }
4962 
4963  return true;
4964 }
4966 //*************************************************************************************************
4967 
4968 
4969 
4970 
4971 //=================================================================================================
4972 //
4973 // EXPRESSION TEMPLATE EVALUATION FUNCTIONS
4974 //
4975 //=================================================================================================
4976 
4977 //*************************************************************************************************
4988 template< typename Type > // Data type of the matrix
4989 template< typename Other > // Data type of the foreign expression
4990 inline bool DynamicMatrix<Type,true>::canAlias( const Other* alias ) const noexcept
4991 {
4992  return static_cast<const void*>( this ) == static_cast<const void*>( alias );
4993 }
4995 //*************************************************************************************************
4996 
4997 
4998 //*************************************************************************************************
5009 template< typename Type > // Data type of the matrix
5010 template< typename Other > // Data type of the foreign expression
5011 inline bool DynamicMatrix<Type,true>::isAliased( const Other* alias ) const noexcept
5012 {
5013  return static_cast<const void*>( this ) == static_cast<const void*>( alias );
5014 }
5016 //*************************************************************************************************
5017 
5018 
5019 //*************************************************************************************************
5029 template< typename Type > // Data type of the matrix
5030 inline bool DynamicMatrix<Type,true>::isAligned() const noexcept
5031 {
5032  return ( usePadding || rows() % SIMDSIZE == 0UL );
5033 }
5035 //*************************************************************************************************
5036 
5037 
5038 //*************************************************************************************************
5049 template< typename Type > // Data type of the matrix
5050 inline bool DynamicMatrix<Type,true>::canSMPAssign() const noexcept
5051 {
5052  return ( rows() * columns() >= SMP_DMATASSIGN_THRESHOLD );
5053 }
5055 //*************************************************************************************************
5056 
5057 
5058 //*************************************************************************************************
5073 template< typename Type > // Data type of the matrix
5075  DynamicMatrix<Type,true>::load( size_t i, size_t j ) const noexcept
5076 {
5077  if( usePadding )
5078  return loada( i, j );
5079  else
5080  return loadu( i, j );
5081 }
5083 //*************************************************************************************************
5084 
5085 
5086 //*************************************************************************************************
5101 template< typename Type > // Data type of the matrix
5103  DynamicMatrix<Type,true>::loada( size_t i, size_t j ) const noexcept
5104 {
5105  using blaze::loada;
5106 
5108 
5109  BLAZE_INTERNAL_ASSERT( i < m_, "Invalid row access index" );
5110  BLAZE_INTERNAL_ASSERT( i + SIMDSIZE <= mm_, "Invalid row access index" );
5111  BLAZE_INTERNAL_ASSERT( !usePadding || i % SIMDSIZE == 0UL, "Invalid row access index" );
5112  BLAZE_INTERNAL_ASSERT( j < n_, "Invalid column access index" );
5113  BLAZE_INTERNAL_ASSERT( checkAlignment( v_+i+j*mm_ ), "Invalid alignment detected" );
5114 
5115  return loada( v_+i+j*mm_ );
5116 }
5118 //*************************************************************************************************
5119 
5120 
5121 //*************************************************************************************************
5136 template< typename Type > // Data type of the matrix
5138  DynamicMatrix<Type,true>::loadu( size_t i, size_t j ) const noexcept
5139 {
5140  using blaze::loadu;
5141 
5143 
5144  BLAZE_INTERNAL_ASSERT( i < m_, "Invalid row access index" );
5145  BLAZE_INTERNAL_ASSERT( i + SIMDSIZE <= mm_, "Invalid row access index" );
5146  BLAZE_INTERNAL_ASSERT( j < n_, "Invalid column access index" );
5147 
5148  return loadu( v_+i+j*mm_ );
5149 }
5151 //*************************************************************************************************
5152 
5153 
5154 //*************************************************************************************************
5170 template< typename Type > // Data type of the matrix
5172  DynamicMatrix<Type,true>::store( size_t i, size_t j, const SIMDType& value ) noexcept
5173 {
5174  if( usePadding )
5175  storea( i, j, value );
5176  else
5177  storeu( i, j, value );
5178 }
5180 //*************************************************************************************************
5181 
5182 
5183 //*************************************************************************************************
5199 template< typename Type > // Data type of the matrix
5201  DynamicMatrix<Type,true>::storea( size_t i, size_t j, const SIMDType& value ) noexcept
5202 {
5203  using blaze::storea;
5204 
5206 
5207  BLAZE_INTERNAL_ASSERT( i < m_, "Invalid row access index" );
5208  BLAZE_INTERNAL_ASSERT( i + SIMDSIZE <= mm_, "Invalid row access index" );
5209  BLAZE_INTERNAL_ASSERT( !usePadding || i % SIMDSIZE == 0UL, "Invalid row access index" );
5210  BLAZE_INTERNAL_ASSERT( j < n_, "Invalid column access index" );
5211  BLAZE_INTERNAL_ASSERT( checkAlignment( v_+i+j*mm_ ), "Invalid alignment detected" );
5212 
5213  storea( v_+i+j*mm_, value );
5214 }
5216 //*************************************************************************************************
5217 
5218 
5219 //*************************************************************************************************
5235 template< typename Type > // Data type of the matrix
5237  DynamicMatrix<Type,true>::storeu( size_t i, size_t j, const SIMDType& value ) noexcept
5238 {
5239  using blaze::storeu;
5240 
5242 
5243  BLAZE_INTERNAL_ASSERT( i < m_, "Invalid row access index" );
5244  BLAZE_INTERNAL_ASSERT( i + SIMDSIZE <= mm_, "Invalid row access index" );
5245  BLAZE_INTERNAL_ASSERT( j < n_, "Invalid column access index" );
5246 
5247  storeu( v_+i+j*mm_, value );
5248 }
5250 //*************************************************************************************************
5251 
5252 
5253 //*************************************************************************************************
5270 template< typename Type > // Data type of the matrix
5272  DynamicMatrix<Type,true>::stream( size_t i, size_t j, const SIMDType& value ) noexcept
5273 {
5274  using blaze::stream;
5275 
5277 
5278  BLAZE_INTERNAL_ASSERT( i < m_, "Invalid row access index" );
5279  BLAZE_INTERNAL_ASSERT( i + SIMDSIZE <= mm_, "Invalid row access index" );
5280  BLAZE_INTERNAL_ASSERT( !usePadding || i % SIMDSIZE == 0UL, "Invalid row access index" );
5281  BLAZE_INTERNAL_ASSERT( j < n_, "Invalid column access index" );
5282  BLAZE_INTERNAL_ASSERT( checkAlignment( v_+i+j*mm_ ), "Invalid alignment detected" );
5283 
5284  stream( v_+i+j*mm_, value );
5285 }
5287 //*************************************************************************************************
5288 
5289 
5290 //*************************************************************************************************
5302 template< typename Type > // Data type of the matrix
5303 template< typename MT > // Type of the right-hand side dense matrix
5304 inline auto DynamicMatrix<Type,true>::assign( const DenseMatrix<MT,true>& rhs )
5305  -> DisableIf_t< VectorizedAssign_v<MT> >
5306 {
5307  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
5308  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
5309 
5310  const size_t ipos( m_ & size_t(-2) );
5311  BLAZE_INTERNAL_ASSERT( ( m_ - ( m_ % 2UL ) ) == ipos, "Invalid end calculation" );
5312 
5313  for( size_t j=0UL; j<n_; ++j ) {
5314  for( size_t i=0UL; i<ipos; i+=2UL ) {
5315  v_[i +j*mm_] = (~rhs)(i ,j);
5316  v_[i+1UL+j*mm_] = (~rhs)(i+1UL,j);
5317  }
5318  if( ipos < m_ ) {
5319  v_[ipos+j*mm_] = (~rhs)(ipos,j);
5320  }
5321  }
5322 }
5324 //*************************************************************************************************
5325 
5326 
5327 //*************************************************************************************************
5339 template< typename Type > // Data type of the matrix
5340 template< typename MT > // Type of the right-hand side dense matrix
5341 inline auto DynamicMatrix<Type,true>::assign( const DenseMatrix<MT,true>& rhs )
5342  -> EnableIf_t< VectorizedAssign_v<MT> >
5343 {
5345 
5346  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
5347  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
5348 
5349  constexpr bool remainder( !usePadding || !IsPadded_v<MT> );
5350 
5351  const size_t ipos( ( remainder )?( m_ & size_t(-SIMDSIZE) ):( m_ ) );
5352  BLAZE_INTERNAL_ASSERT( !remainder || ( m_ - ( m_ % (SIMDSIZE) ) ) == ipos, "Invalid end calculation" );
5353 
5354  if( usePadding && useStreaming &&
5355  ( m_*n_ > ( cacheSize / ( sizeof(Type) * 3UL ) ) ) && !(~rhs).isAliased( this ) )
5356  {
5357  for( size_t j=0UL; j<n_; ++j )
5358  {
5359  size_t i( 0UL );
5360  Iterator left( begin(j) );
5361  ConstIterator_t<MT> right( (~rhs).begin(j) );
5362 
5363  for( ; i<ipos; i+=SIMDSIZE ) {
5364  left.stream( right.load() ); left += SIMDSIZE; right += SIMDSIZE;
5365  }
5366  for( ; remainder && i<m_; ++i ) {
5367  *left = *right; ++left; ++right;
5368  }
5369  }
5370  }
5371  else
5372  {
5373  for( size_t j=0UL; j<n_; ++j )
5374  {
5375  size_t i( 0UL );
5376  Iterator left( begin(j) );
5377  ConstIterator_t<MT> right( (~rhs).begin(j) );
5378 
5379  for( ; (i+SIMDSIZE*3UL) < ipos; i+=SIMDSIZE*4UL ) {
5380  left.store( right.load() ); left += SIMDSIZE; right += SIMDSIZE;
5381  left.store( right.load() ); left += SIMDSIZE; right += SIMDSIZE;
5382  left.store( right.load() ); left += SIMDSIZE; right += SIMDSIZE;
5383  left.store( right.load() ); left += SIMDSIZE; right += SIMDSIZE;
5384  }
5385  for( ; i<ipos; i+=SIMDSIZE ) {
5386  left.store( right.load() ); left += SIMDSIZE; right += SIMDSIZE;
5387  }
5388  for( ; remainder && i<m_; ++i ) {
5389  *left = *right; ++left; ++right;
5390  }
5391  }
5392  }
5393 }
5395 //*************************************************************************************************
5396 
5397 
5398 //*************************************************************************************************
5410 template< typename Type > // Data type of the matrix
5411 template< typename MT > // Type of the right-hand side dense matrix
5412 inline void DynamicMatrix<Type,true>::assign( const DenseMatrix<MT,false>& rhs )
5413 {
5415 
5416  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
5417  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
5418 
5419  constexpr size_t block( BLOCK_SIZE );
5420 
5421  for( size_t jj=0UL; jj<n_; jj+=block ) {
5422  const size_t jend( min( n_, jj+block ) );
5423  for( size_t ii=0UL; ii<m_; ii+=block ) {
5424  const size_t iend( min( m_, ii+block ) );
5425  for( size_t j=jj; j<jend; ++j ) {
5426  for( size_t i=ii; i<iend; ++i ) {
5427  v_[i+j*mm_] = (~rhs)(i,j);
5428  }
5429  }
5430  }
5431  }
5432 }
5434 //*************************************************************************************************
5435 
5436 
5437 //*************************************************************************************************
5449 template< typename Type > // Data type of the matrix
5450 template< typename MT > // Type of the right-hand side sparse matrix
5451 inline void DynamicMatrix<Type,true>::assign( const SparseMatrix<MT,true>& rhs )
5452 {
5453  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
5454  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
5455 
5456  for( size_t j=0UL; j<(~rhs).columns(); ++j )
5457  for( auto element=(~rhs).begin(j); element!=(~rhs).end(j); ++element )
5458  v_[element->index()+j*mm_] = element->value();
5459 }
5461 //*************************************************************************************************
5462 
5463 
5464 //*************************************************************************************************
5476 template< typename Type > // Data type of the matrix
5477 template< typename MT > // Type of the right-hand side sparse matrix
5478 inline void DynamicMatrix<Type,true>::assign( const SparseMatrix<MT,false>& rhs )
5479 {
5481 
5482  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
5483  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
5484 
5485  for( size_t i=0UL; i<(~rhs).rows(); ++i )
5486  for( auto element=(~rhs).begin(i); element!=(~rhs).end(i); ++element )
5487  v_[i+element->index()*mm_] = element->value();
5488 }
5490 //*************************************************************************************************
5491 
5492 
5493 //*************************************************************************************************
5505 template< typename Type > // Data type of the matrix
5506 template< typename MT > // Type of the right-hand side dense matrix
5507 inline auto DynamicMatrix<Type,true>::addAssign( const DenseMatrix<MT,true>& rhs )
5508  -> DisableIf_t< VectorizedAddAssign_v<MT> >
5509 {
5510  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
5511  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
5512 
5513  for( size_t j=0UL; j<n_; ++j )
5514  {
5515  if( IsDiagonal_v<MT> )
5516  {
5517  v_[j+j*mm_] += (~rhs)(j,j);
5518  }
5519  else
5520  {
5521  const size_t ibegin( ( IsLower_v<MT> )
5522  ?( IsStrictlyLower_v<MT> ? j+1UL : j )
5523  :( 0UL ) );
5524  const size_t iend ( ( IsUpper_v<MT> )
5525  ?( IsStrictlyUpper_v<MT> ? j : j+1UL )
5526  :( m_ ) );
5527  BLAZE_INTERNAL_ASSERT( ibegin <= iend, "Invalid loop indices detected" );
5528 
5529  size_t i( ibegin );
5530 
5531  for( ; (i+2UL) <= iend; i+=2UL ) {
5532  v_[i +j*mm_] += (~rhs)(i ,j);
5533  v_[i+1UL+j*mm_] += (~rhs)(i+1UL,j);
5534  }
5535  if( i < iend ) {
5536  v_[i+j*mm_] += (~rhs)(i,j);
5537  }
5538  }
5539  }
5540 }
5542 //*************************************************************************************************
5543 
5544 
5545 //*************************************************************************************************
5557 template< typename Type > // Data type of the matrix
5558 template< typename MT > // Type of the right-hand side dense matrix
5559 inline auto DynamicMatrix<Type,true>::addAssign( const DenseMatrix<MT,true>& rhs )
5560  -> EnableIf_t< VectorizedAddAssign_v<MT> >
5561 {
5564 
5565  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
5566  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
5567 
5568  constexpr bool remainder( !usePadding || !IsPadded_v<MT> );
5569 
5570  for( size_t j=0UL; j<n_; ++j )
5571  {
5572  const size_t ibegin( ( IsLower_v<MT> )
5573  ?( ( IsStrictlyLower_v<MT> ? j+1UL : j ) & size_t(-SIMDSIZE) )
5574  :( 0UL ) );
5575  const size_t iend ( ( IsUpper_v<MT> )
5576  ?( IsStrictlyUpper_v<MT> ? j : j+1UL )
5577  :( m_ ) );
5578  BLAZE_INTERNAL_ASSERT( ibegin <= iend, "Invalid loop indices detected" );
5579 
5580  const size_t ipos( ( remainder )?( iend & size_t(-SIMDSIZE) ):( iend ) );
5581  BLAZE_INTERNAL_ASSERT( !remainder || ( iend - ( iend % (SIMDSIZE) ) ) == ipos, "Invalid end calculation" );
5582 
5583  size_t i( ibegin );
5584  Iterator left( begin(j) + ibegin );
5585  ConstIterator_t<MT> right( (~rhs).begin(j) + ibegin );
5586 
5587  for( ; (i+SIMDSIZE*3UL) < ipos; i+=SIMDSIZE*4UL ) {
5588  left.store( left.load() + right.load() ); left += SIMDSIZE; right += SIMDSIZE;
5589  left.store( left.load() + right.load() ); left += SIMDSIZE; right += SIMDSIZE;
5590  left.store( left.load() + right.load() ); left += SIMDSIZE; right += SIMDSIZE;
5591  left.store( left.load() + right.load() ); left += SIMDSIZE; right += SIMDSIZE;
5592  }
5593  for( ; i<ipos; i+=SIMDSIZE ) {
5594  left.store( left.load() + right.load() ); left += SIMDSIZE; right += SIMDSIZE;
5595  }
5596  for( ; remainder && i<iend; ++i ) {
5597  *left += *right; ++left; ++right;
5598  }
5599  }
5600 }
5602 //*************************************************************************************************
5603 
5604 
5605 //*************************************************************************************************
5617 template< typename Type > // Data type of the matrix
5618 template< typename MT > // Type of the right-hand side dense matrix
5619 inline void DynamicMatrix<Type,true>::addAssign( const DenseMatrix<MT,false>& rhs )
5620 {
5622 
5623  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
5624  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
5625 
5626  constexpr size_t block( BLOCK_SIZE );
5627 
5628  for( size_t jj=0UL; jj<n_; jj+=block ) {
5629  const size_t jend( min( n_, jj+block ) );
5630  for( size_t ii=0UL; ii<m_; ii+=block )
5631  {
5632  if( IsLower_v<MT> && ii < jj ) continue;
5633  if( IsUpper_v<MT> && ii > jj ) break;
5634 
5635  for( size_t j=jj; j<jend; ++j )
5636  {
5637  const size_t ibegin( ( IsLower_v<MT> )
5638  ?( max( ( IsStrictlyLower_v<MT> ? j+1UL : j ), ii ) )
5639  :( ii ) );
5640  const size_t iend ( ( IsUpper_v<MT> )
5641  ?( min( ( IsStrictlyUpper_v<MT> ? j : j+1UL ), m_, ii+block ) )
5642  :( min( m_, ii+block ) ) );
5643  BLAZE_INTERNAL_ASSERT( ibegin <= iend, "Invalid loop indices detected" );
5644 
5645  for( size_t i=ibegin; i<iend; ++i ) {
5646  v_[i+j*mm_] += (~rhs)(i,j);
5647  }
5648  }
5649  }
5650  }
5651 }
5653 //*************************************************************************************************
5654 
5655 
5656 //*************************************************************************************************
5668 template< typename Type > // Data type of the matrix
5669 template< typename MT > // Type of the right-hand side sparse matrix
5670 inline void DynamicMatrix<Type,true>::addAssign( const SparseMatrix<MT,true>& rhs )
5671 {
5672  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
5673  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
5674 
5675  for( size_t j=0UL; j<(~rhs).columns(); ++j )
5676  for( auto element=(~rhs).begin(j); element!=(~rhs).end(j); ++element )
5677  v_[element->index()+j*mm_] += element->value();
5678 }
5680 //*************************************************************************************************
5681 
5682 
5683 //*************************************************************************************************
5695 template< typename Type > // Data type of the matrix
5696 template< typename MT > // Type of the right-hand side sparse matrix
5697 inline void DynamicMatrix<Type,true>::addAssign( const SparseMatrix<MT,false>& rhs )
5698 {
5700 
5701  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
5702  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
5703 
5704  for( size_t i=0UL; i<(~rhs).rows(); ++i )
5705  for( auto element=(~rhs).begin(i); element!=(~rhs).end(i); ++element )
5706  v_[i+element->index()*mm_] += element->value();
5707 }
5709 //*************************************************************************************************
5710 
5711 
5712 //*************************************************************************************************
5724 template< typename Type > // Data type of the matrix
5725 template< typename MT > // Type of the right-hand side dense matrix
5726 inline auto DynamicMatrix<Type,true>::subAssign( const DenseMatrix<MT,true>& rhs )
5727  -> DisableIf_t< VectorizedSubAssign_v<MT> >
5728 {
5729  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
5730  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
5731 
5732  for( size_t j=0UL; j<n_; ++j )
5733  {
5734  if( IsDiagonal_v<MT> )
5735  {
5736  v_[j+j*mm_] -= (~rhs)(j,j);
5737  }
5738  else
5739  {
5740  const size_t ibegin( ( IsLower_v<MT> )
5741  ?( IsStrictlyLower_v<MT> ? j+1UL : j )
5742  :( 0UL ) );
5743  const size_t iend ( ( IsUpper_v<MT> )
5744  ?( IsStrictlyUpper_v<MT> ? j : j+1UL )
5745  :( m_ ) );
5746  BLAZE_INTERNAL_ASSERT( ibegin <= iend, "Invalid loop indices detected" );
5747 
5748  size_t i( ibegin );
5749 
5750  for( ; (i+2UL) <= iend; i+=2UL ) {
5751  v_[i +j*mm_] -= (~rhs)(i ,j);
5752  v_[i+1+j*mm_] -= (~rhs)(i+1,j);
5753  }
5754  if( i < iend ) {
5755  v_[i+j*mm_] -= (~rhs)(i,j);
5756  }
5757  }
5758  }
5759 }
5761 //*************************************************************************************************
5762 
5763 
5764 //*************************************************************************************************
5776 template< typename Type > // Data type of the matrix
5777 template< typename MT > // Type of the right-hand side dense matrix
5778 inline auto DynamicMatrix<Type,true>::subAssign( const DenseMatrix<MT,true>& rhs )
5779  -> EnableIf_t< VectorizedSubAssign_v<MT> >
5780 {
5783 
5784  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
5785  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
5786 
5787  constexpr bool remainder( !usePadding || !IsPadded_v<MT> );
5788 
5789  for( size_t j=0UL; j<n_; ++j )
5790  {
5791  const size_t ibegin( ( IsLower_v<MT> )
5792  ?( ( IsStrictlyLower_v<MT> ? j+1UL : j ) & size_t(-SIMDSIZE) )
5793  :( 0UL ) );
5794  const size_t iend ( ( IsUpper_v<MT> )
5795  ?( IsStrictlyUpper_v<MT> ? j : j+1UL )
5796  :( m_ ) );
5797  BLAZE_INTERNAL_ASSERT( ibegin <= iend, "Invalid loop indices detected" );
5798 
5799  const size_t ipos( ( remainder )?( iend & size_t(-SIMDSIZE) ):( iend ) );
5800  BLAZE_INTERNAL_ASSERT( !remainder || ( iend - ( iend % (SIMDSIZE) ) ) == ipos, "Invalid end calculation" );
5801 
5802  size_t i( ibegin );
5803  Iterator left( begin(j) + ibegin );
5804  ConstIterator_t<MT> right( (~rhs).begin(j) + ibegin );
5805 
5806  for( ; (i+SIMDSIZE*3UL) < ipos; i+=SIMDSIZE*4UL ) {
5807  left.store( left.load() - right.load() ); left += SIMDSIZE; right += SIMDSIZE;
5808  left.store( left.load() - right.load() ); left += SIMDSIZE; right += SIMDSIZE;
5809  left.store( left.load() - right.load() ); left += SIMDSIZE; right += SIMDSIZE;
5810  left.store( left.load() - right.load() ); left += SIMDSIZE; right += SIMDSIZE;
5811  }
5812  for( ; i<ipos; i+=SIMDSIZE ) {
5813  left.store( left.load() - right.load() ); left += SIMDSIZE; right += SIMDSIZE;
5814  }
5815  for( ; remainder && i<iend; ++i ) {
5816  *left -= *right; ++left; ++right;
5817  }
5818  }
5819 }
5821 //*************************************************************************************************
5822 
5823 
5824 //*************************************************************************************************
5836 template< typename Type > // Data type of the matrix
5837 template< typename MT > // Type of the right-hand side dense matrix
5838 inline void DynamicMatrix<Type,true>::subAssign( const DenseMatrix<MT,false>& rhs )
5839 {
5841 
5842  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
5843  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
5844 
5845  constexpr size_t block( BLOCK_SIZE );
5846 
5847  for( size_t jj=0UL; jj<n_; jj+=block ) {
5848  const size_t jend( min( n_, jj+block ) );
5849  for( size_t ii=0UL; ii<m_; ii+=block )
5850  {
5851  if( IsLower_v<MT> && ii < jj ) continue;
5852  if( IsUpper_v<MT> && ii > jj ) break;
5853 
5854  for( size_t j=jj; j<jend; ++j )
5855  {
5856  const size_t ibegin( ( IsLower_v<MT> )
5857  ?( max( ( IsStrictlyLower_v<MT> ? j+1UL : j ), ii ) )
5858  :( ii ) );
5859  const size_t iend ( ( IsUpper_v<MT> )
5860  ?( min( ( IsStrictlyUpper_v<MT> ? j : j+1UL ), m_, ii+block ) )
5861  :( min( m_, ii+block ) ) );
5862  BLAZE_INTERNAL_ASSERT( ibegin <= iend, "Invalid loop indices detected" );
5863 
5864  for( size_t i=ibegin; i<iend; ++i ) {
5865  v_[i+j*mm_] -= (~rhs)(i,j);
5866  }
5867  }
5868  }
5869  }
5870 }
5872 //*************************************************************************************************
5873 
5874 
5875 //*************************************************************************************************
5887 template< typename Type > // Data type of the matrix
5888 template< typename MT > // Type of the right-hand side sparse matrix
5889 inline void DynamicMatrix<Type,true>::subAssign( const SparseMatrix<MT,true>& rhs )
5890 {
5891  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
5892  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
5893 
5894  for( size_t j=0UL; j<(~rhs).columns(); ++j )
5895  for( auto element=(~rhs).begin(j); element!=(~rhs).end(j); ++element )
5896  v_[element->index()+j*mm_] -= element->value();
5897 }
5899 //*************************************************************************************************
5900 
5901 
5902 //*************************************************************************************************
5914 template< typename Type > // Data type of the matrix
5915 template< typename MT > // Type of the right-hand side sparse matrix
5916 inline void DynamicMatrix<Type,true>::subAssign( const SparseMatrix<MT,false>& rhs )
5917 {
5919 
5920  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
5921  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
5922 
5923  for( size_t i=0UL; i<(~rhs).rows(); ++i )
5924  for( auto element=(~rhs).begin(i); element!=(~rhs).end(i); ++element )
5925  v_[i+element->index()*mm_] -= element->value();
5926 }
5928 //*************************************************************************************************
5929 
5930 
5931 //*************************************************************************************************
5943 template< typename Type > // Data type of the matrix
5944 template< typename MT > // Type of the right-hand side dense matrix
5945 inline auto DynamicMatrix<Type,true>::schurAssign( const DenseMatrix<MT,true>& rhs )
5946  -> DisableIf_t< VectorizedSchurAssign_v<MT> >
5947 {
5948  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
5949  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
5950 
5951  const size_t ipos( m_ & size_t(-2) );
5952  BLAZE_INTERNAL_ASSERT( ( m_ - ( m_ % 2UL ) ) == ipos, "Invalid end calculation" );
5953 
5954  for( size_t j=0UL; j<n_; ++j ) {
5955  for( size_t i=0UL; (i+2UL) <= ipos; i+=2UL ) {
5956  v_[i +j*mm_] *= (~rhs)(i ,j);
5957  v_[i+1+j*mm_] *= (~rhs)(i+1,j);
5958  }
5959  if( ipos < m_ ) {
5960  v_[ipos+j*mm_] *= (~rhs)(ipos,j);
5961  }
5962  }
5963 }
5965 //*************************************************************************************************
5966 
5967 
5968 //*************************************************************************************************
5980 template< typename Type > // Data type of the matrix
5981 template< typename MT > // Type of the right-hand side dense matrix
5982 inline auto DynamicMatrix<Type,true>::schurAssign( const DenseMatrix<MT,true>& rhs )
5983  -> EnableIf_t< VectorizedSchurAssign_v<MT> >
5984 {
5986 
5987  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
5988  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
5989 
5990  constexpr bool remainder( !usePadding || !IsPadded_v<MT> );
5991 
5992  for( size_t j=0UL; j<n_; ++j )
5993  {
5994  const size_t ipos( ( remainder )?( m_ & size_t(-SIMDSIZE) ):( m_ ) );
5995  BLAZE_INTERNAL_ASSERT( !remainder || ( m_ - ( m_ % (SIMDSIZE) ) ) == ipos, "Invalid end calculation" );
5996 
5997  size_t i( 0UL );
5998  Iterator left( begin(j) );
5999  ConstIterator_t<MT> right( (~rhs).begin(j) );
6000 
6001  for( ; (i+SIMDSIZE*3UL) < ipos; i+=SIMDSIZE*4UL ) {
6002  left.store( left.load() * right.load() ); left += SIMDSIZE; right += SIMDSIZE;
6003  left.store( left.load() * right.load() ); left += SIMDSIZE; right += SIMDSIZE;
6004  left.store( left.load() * right.load() ); left += SIMDSIZE; right += SIMDSIZE;
6005  left.store( left.load() * right.load() ); left += SIMDSIZE; right += SIMDSIZE;
6006  }
6007  for( ; i<ipos; i+=SIMDSIZE ) {
6008  left.store( left.load() * right.load() ); left += SIMDSIZE; right += SIMDSIZE;
6009  }
6010  for( ; remainder && i<m_; ++i ) {
6011  *left *= *right; ++left; ++right;
6012  }
6013  }
6014 }
6016 //*************************************************************************************************
6017 
6018 
6019 //*************************************************************************************************
6031 template< typename Type > // Data type of the matrix
6032 template< typename MT > // Type of the right-hand side dense matrix
6033 inline void DynamicMatrix<Type,true>::schurAssign( const DenseMatrix<MT,false>& rhs )
6034 {
6036 
6037  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
6038  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
6039 
6040  constexpr size_t block( BLOCK_SIZE );
6041 
6042  for( size_t jj=0UL; jj<n_; jj+=block ) {
6043  const size_t jend( min( n_, jj+block ) );
6044  for( size_t ii=0UL; ii<m_; ii+=block ) {
6045  const size_t iend( min( m_, ii+block ) );
6046  for( size_t j=jj; j<jend; ++j ) {
6047  for( size_t i=ii; i<iend; ++i ) {
6048  v_[i+j*mm_] *= (~rhs)(i,j);
6049  }
6050  }
6051  }
6052  }
6053 }
6055 //*************************************************************************************************
6056 
6057 
6058 //*************************************************************************************************
6070 template< typename Type > // Data type of the matrix
6071 template< typename MT > // Type of the right-hand side sparse matrix
6072 inline void DynamicMatrix<Type,true>::schurAssign( const SparseMatrix<MT,true>& rhs )
6073 {
6074  using blaze::reset;
6075 
6076  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
6077  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
6078 
6079  for( size_t j=0UL; j<n_; ++j )
6080  {
6081  size_t i( 0UL );
6082 
6083  for( auto element=(~rhs).begin(j); element!=(~rhs).end(j); ++element ) {
6084  for( ; i<element->index(); ++i )
6085  reset( v_[i+j*mm_] );
6086  v_[i+j*mm_] *= element->value();
6087  ++i;
6088  }
6089 
6090  for( ; i<m_; ++i ) {
6091  reset( v_[i+j*mm_] );
6092  }
6093  }
6094 }
6096 //*************************************************************************************************
6097 
6098 
6099 //*************************************************************************************************
6111 template< typename Type > // Data type of the matrix
6112 template< typename MT > // Type of the right-hand side sparse matrix
6113 inline void DynamicMatrix<Type,true>::schurAssign( const SparseMatrix<MT,false>& rhs )
6114 {
6115  using blaze::reset;
6116 
6118 
6119  BLAZE_INTERNAL_ASSERT( m_ == (~rhs).rows() , "Invalid number of rows" );
6120  BLAZE_INTERNAL_ASSERT( n_ == (~rhs).columns(), "Invalid number of columns" );
6121 
6122  for( size_t i=0UL; i<m_; ++i )
6123  {
6124  size_t j( 0UL );
6125 
6126  for( auto element=(~rhs).begin(i); element!=(~rhs).end(i); ++element ) {
6127  for( ; j<element->index(); ++j )
6128  reset( v_[i+j*mm_] );
6129  v_[i+j*mm_] *= element->value();
6130  ++j;
6131  }
6132 
6133  for( ; j<n_; ++j ) {
6134  reset( v_[i+j*mm_] );
6135  }
6136  }
6137 }
6139 //*************************************************************************************************
6140 
6141 
6142 
6143 
6144 
6145 
6146 
6147 
6148 //=================================================================================================
6149 //
6150 // DYNAMICMATRIX OPERATORS
6151 //
6152 //=================================================================================================
6153 
6154 //*************************************************************************************************
6157 template< typename Type, bool SO >
6158 void reset( DynamicMatrix<Type,SO>& m );
6159 
6160 template< typename Type, bool SO >
6161 void reset( DynamicMatrix<Type,SO>& m, size_t i );
6162 
6163 template< typename Type, bool SO >
6164 void clear( DynamicMatrix<Type,SO>& m );
6165 
6166 template< bool RF, typename Type, bool SO >
6167 bool isDefault( const DynamicMatrix<Type,SO>& m );
6168 
6169 template< typename Type, bool SO >
6170 bool isIntact( const DynamicMatrix<Type,SO>& m ) noexcept;
6171 
6172 template< typename Type, bool SO >
6173 void swap( DynamicMatrix<Type,SO>& a, DynamicMatrix<Type,SO>& b ) noexcept;
6175 //*************************************************************************************************
6176 
6177 
6178 //*************************************************************************************************
6185 template< typename Type // Data type of the matrix
6186  , bool SO > // Storage order
6188 {
6189  m.reset();
6190 }
6191 //*************************************************************************************************
6192 
6193 
6194 //*************************************************************************************************
6207 template< typename Type // Data type of the matrix
6208  , bool SO > // Storage order
6209 inline void reset( DynamicMatrix<Type,SO>& m, size_t i )
6210 {
6211  m.reset( i );
6212 }
6213 //*************************************************************************************************
6214 
6215 
6216 //*************************************************************************************************
6223 template< typename Type // Data type of the matrix
6224  , bool SO > // Storage order
6226 {
6227  m.clear();
6228 }
6229 //*************************************************************************************************
6230 
6231 
6232 //*************************************************************************************************
6257 template< bool RF // Relaxation flag
6258  , typename Type // Data type of the matrix
6259  , bool SO > // Storage order
6260 inline bool isDefault( const DynamicMatrix<Type,SO>& m )
6261 {
6262  return ( m.rows() == 0UL && m.columns() == 0UL );
6263 }
6264 //*************************************************************************************************
6265 
6266 
6267 //*************************************************************************************************
6285 template< typename Type // Data type of the matrix
6286  , bool SO > // Storage order
6287 inline bool isIntact( const DynamicMatrix<Type,SO>& m ) noexcept
6288 {
6289  return m.isIntact();
6290 }
6291 //*************************************************************************************************
6292 
6293 
6294 //*************************************************************************************************
6302 template< typename Type // Data type of the matrix
6303  , bool SO > // Storage order
6305 {
6306  a.swap( b );
6307 }
6308 //*************************************************************************************************
6309 
6310 
6311 
6312 
6313 //=================================================================================================
6314 //
6315 // HASCONSTDATAACCESS SPECIALIZATIONS
6316 //
6317 //=================================================================================================
6318 
6319 //*************************************************************************************************
6321 template< typename T, bool SO >
6322 struct HasConstDataAccess< DynamicMatrix<T,SO> >
6323  : public TrueType
6324 {};
6326 //*************************************************************************************************
6327 
6328 
6329 
6330 
6331 //=================================================================================================
6332 //
6333 // HASMUTABLEDATAACCESS SPECIALIZATIONS
6334 //
6335 //=================================================================================================
6336 
6337 //*************************************************************************************************
6339 template< typename T, bool SO >
6340 struct HasMutableDataAccess< DynamicMatrix<T,SO> >
6341  : public TrueType
6342 {};
6344 //*************************************************************************************************
6345 
6346 
6347 
6348 
6349 //=================================================================================================
6350 //
6351 // ISALIGNED SPECIALIZATIONS
6352 //
6353 //=================================================================================================
6354 
6355 //*************************************************************************************************
6357 template< typename T, bool SO >
6358 struct IsAligned< DynamicMatrix<T,SO> >
6359  : public BoolConstant<usePadding>
6360 {};
6362 //*************************************************************************************************
6363 
6364 
6365 
6366 
6367 //=================================================================================================
6368 //
6369 // ISCONTIGUOUS SPECIALIZATIONS
6370 //
6371 //=================================================================================================
6372 
6373 //*************************************************************************************************
6375 template< typename T, bool SO >
6376 struct IsContiguous< DynamicMatrix<T,SO> >
6377  : public TrueType
6378 {};
6380 //*************************************************************************************************
6381 
6382 
6383 
6384 
6385 //=================================================================================================
6386 //
6387 // ISPADDED SPECIALIZATIONS
6388 //
6389 //=================================================================================================
6390 
6391 //*************************************************************************************************
6393 template< typename T, bool SO >
6394 struct IsPadded< DynamicMatrix<T,SO> >
6395  : public BoolConstant<usePadding>
6396 {};
6398 //*************************************************************************************************
6399 
6400 
6401 
6402 
6403 //=================================================================================================
6404 //
6405 // ISRESIZABLE SPECIALIZATIONS
6406 //
6407 //=================================================================================================
6408 
6409 //*************************************************************************************************
6411 template< typename T, bool SO >
6412 struct IsResizable< DynamicMatrix<T,SO> >
6413  : public TrueType
6414 {};
6416 //*************************************************************************************************
6417 
6418 
6419 
6420 
6421 //=================================================================================================
6422 //
6423 // ISSHRINKABLE SPECIALIZATIONS
6424 //
6425 //=================================================================================================
6426 
6427 //*************************************************************************************************
6429 template< typename T, bool SO >
6430 struct IsShrinkable< DynamicMatrix<T,SO> >
6431  : public TrueType
6432 {};
6434 //*************************************************************************************************
6435 
6436 
6437 
6438 
6439 //=================================================================================================
6440 //
6441 // ADDTRAIT SPECIALIZATIONS
6442 //
6443 //=================================================================================================
6444 
6445 //*************************************************************************************************
6447 template< typename T1, typename T2 >
6448 struct AddTraitEval2< T1, T2
6449  , EnableIf_t< IsMatrix_v<T1> &&
6450  IsMatrix_v<T2> &&
6451  ( IsDenseMatrix_v<T1> || IsDenseMatrix_v<T2> ) &&
6452  ( Size_v<T1,0UL> == DefaultSize_v ) &&
6453  ( Size_v<T2,0UL> == DefaultSize_v ) &&
6454  ( Size_v<T1,1UL> == DefaultSize_v ) &&
6455  ( Size_v<T2,1UL> == DefaultSize_v ) &&
6456  ( MaxSize_v<T1,0UL> == DefaultMaxSize_v ) &&
6457  ( MaxSize_v<T2,0UL> == DefaultMaxSize_v ) &&
6458  ( MaxSize_v<T1,1UL> == DefaultMaxSize_v ) &&
6459  ( MaxSize_v<T2,1UL> == DefaultMaxSize_v ) > >
6460 {
6461  using ET1 = ElementType_t<T1>;
6462  using ET2 = ElementType_t<T2>;
6463 
6464  static constexpr bool SO1 = StorageOrder_v<T1>;
6465  static constexpr bool SO2 = StorageOrder_v<T2>;
6466 
6467  static constexpr bool SO = ( IsDenseMatrix_v<T1> && IsDenseMatrix_v<T2>
6468  ? ( IsSymmetric_v<T1> ^ IsSymmetric_v<T2>
6469  ? ( IsSymmetric_v<T1>
6470  ? SO2
6471  : SO1 )
6472  : SO1 && SO2 )
6473  : ( IsDenseMatrix_v<T1>
6474  ? SO1
6475  : SO2 ) );
6476 
6477  using Type = DynamicMatrix< AddTrait_t<ET1,ET2>, SO >;
6478 };
6480 //*************************************************************************************************
6481 
6482 
6483 
6484 
6485 //=================================================================================================
6486 //
6487 // SUBTRAIT SPECIALIZATIONS
6488 //
6489 //=================================================================================================
6490 
6491 //*************************************************************************************************
6493 template< typename T1, typename T2 >
6494 struct SubTraitEval2< T1, T2
6495  , EnableIf_t< IsMatrix_v<T1> &&
6496  IsMatrix_v<T2> &&
6497  ( IsDenseMatrix_v<T1> || IsDenseMatrix_v<T2> ) &&
6498  ( Size_v<T1,0UL> == DefaultSize_v ) &&
6499  ( Size_v<T2,0UL> == DefaultSize_v ) &&
6500  ( Size_v<T1,1UL> == DefaultSize_v ) &&
6501  ( Size_v<T2,1UL> == DefaultSize_v ) &&
6502  ( MaxSize_v<T1,0UL> == DefaultMaxSize_v ) &&
6503  ( MaxSize_v<T2,0UL> == DefaultMaxSize_v ) &&
6504  ( MaxSize_v<T1,1UL> == DefaultMaxSize_v ) &&
6505  ( MaxSize_v<T2,1UL> == DefaultMaxSize_v ) > >
6506 {
6507  using ET1 = ElementType_t<T1>;
6508  using ET2 = ElementType_t<T2>;
6509 
6510  static constexpr bool SO1 = StorageOrder_v<T1>;
6511  static constexpr bool SO2 = StorageOrder_v<T2>;
6512 
6513  static constexpr bool SO = ( IsDenseMatrix_v<T1> && IsDenseMatrix_v<T2>
6514  ? ( IsSymmetric_v<T1> ^ IsSymmetric_v<T2>
6515  ? ( IsSymmetric_v<T1>
6516  ? SO2
6517  : SO1 )
6518  : SO1 && SO2 )
6519  : ( IsDenseMatrix_v<T1>
6520  ? SO1
6521  : SO2 ) );
6522 
6523  using Type = DynamicMatrix< SubTrait_t<ET1,ET2>, SO >;
6524 };
6526 //*************************************************************************************************
6527 
6528 
6529 
6530 
6531 //=================================================================================================
6532 //
6533 // SCHURTRAIT SPECIALIZATIONS
6534 //
6535 //=================================================================================================
6536 
6537 //*************************************************************************************************
6539 template< typename T1, typename T2 >
6540 struct SchurTraitEval2< T1, T2
6541  , EnableIf_t< IsDenseMatrix_v<T1> &&
6542  IsDenseMatrix_v<T2> &&
6543  ( Size_v<T1,0UL> == DefaultSize_v ) &&
6544  ( Size_v<T2,0UL> == DefaultSize_v ) &&
6545  ( Size_v<T1,1UL> == DefaultSize_v ) &&
6546  ( Size_v<T2,1UL> == DefaultSize_v ) &&
6547  ( MaxSize_v<T1,0UL> == DefaultMaxSize_v ) &&
6548  ( MaxSize_v<T2,0UL> == DefaultMaxSize_v ) &&
6549  ( MaxSize_v<T1,1UL> == DefaultMaxSize_v ) &&
6550  ( MaxSize_v<T2,1UL> == DefaultMaxSize_v ) > >
6551 {
6552  using ET1 = ElementType_t<T1>;
6553  using ET2 = ElementType_t<T2>;
6554 
6555  static constexpr bool SO1 = StorageOrder_v<T1>;
6556  static constexpr bool SO2 = StorageOrder_v<T2>;
6557 
6558  static constexpr bool SO = ( IsSymmetric_v<T1> ^ IsSymmetric_v<T2>
6559  ? ( IsSymmetric_v<T1>
6560  ? SO2
6561  : SO1 )
6562  : SO1 && SO2 );
6563 
6564  using Type = DynamicMatrix< MultTrait_t<ET1,ET2>, SO >;
6565 };
6567 //*************************************************************************************************
6568 
6569 
6570 
6571 
6572 //=================================================================================================
6573 //
6574 // MULTTRAIT SPECIALIZATIONS
6575 //
6576 //=================================================================================================
6577 
6578 //*************************************************************************************************
6580 template< typename T1, typename T2 >
6581 struct MultTraitEval2< T1, T2
6582  , EnableIf_t< IsDenseMatrix_v<T1> &&
6583  IsNumeric_v<T2> &&
6584  ( Size_v<T1,0UL> == DefaultSize_v ) &&
6585  ( Size_v<T1,1UL> == DefaultSize_v ) &&
6586  ( MaxSize_v<T1,0UL> == DefaultMaxSize_v ) &&
6587  ( MaxSize_v<T1,1UL> == DefaultMaxSize_v ) > >
6588 {
6589  using ET1 = ElementType_t<T1>;
6590 
6591  using Type = DynamicMatrix< MultTrait_t<ET1,T2>, StorageOrder_v<T1> >;
6592 };
6593 
6594 template< typename T1, typename T2 >
6595 struct MultTraitEval2< T1, T2
6596  , EnableIf_t< IsNumeric_v<T1> &&
6597  IsDenseMatrix_v<T2> &&
6598  ( Size_v<T2,0UL> == DefaultSize_v ) &&
6599  ( Size_v<T2,1UL> == DefaultSize_v ) &&
6600  ( MaxSize_v<T2,0UL> == DefaultMaxSize_v ) &&
6601  ( MaxSize_v<T2,1UL> == DefaultMaxSize_v ) > >
6602 {
6603  using ET2 = ElementType_t<T2>;
6604 
6605  using Type = DynamicMatrix< MultTrait_t<T1,ET2>, StorageOrder_v<T2> >;
6606 };
6607 
6608 template< typename T1, typename T2 >
6609 struct MultTraitEval2< T1, T2
6610  , EnableIf_t< IsDenseVector_v<T1> &&
6611  IsDenseVector_v<T2> &&
6612  IsColumnVector_v<T1> &&
6613  IsRowVector_v<T2> &&
6614  ( ( Size_v<T1,0UL> == DefaultSize_v ) ||
6615  ( Size_v<T2,0UL> == DefaultSize_v ) ) &&
6616  ( ( MaxSize_v<T1,0UL> == DefaultMaxSize_v ) ||
6617  ( MaxSize_v<T2,0UL> == DefaultMaxSize_v ) ) > >
6618 {
6619  using ET1 = ElementType_t<T1>;
6620  using ET2 = ElementType_t<T2>;
6621 
6622  using Type = DynamicMatrix< MultTrait_t<ET1,ET2>, false >;
6623 };
6624 
6625 template< typename T1, typename T2 >
6626 struct MultTraitEval2< T1, T2
6627  , EnableIf_t< IsMatrix_v<T1> &&
6628  IsMatrix_v<T2> &&
6629  ( IsDenseMatrix_v<T1> || IsDenseMatrix_v<T2> ) &&
6630  ( ( Size_v<T1,0UL> == DefaultSize_v &&
6631  ( !IsSquare_v<T1> || Size_v<T2,0UL> == DefaultSize_v ) ) ||
6632  ( Size_v<T2,1UL> == DefaultSize_v &&
6633  ( !IsSquare_v<T2> || Size_v<T1,1UL> == DefaultSize_v ) ) ) &&
6634  ( ( MaxSize_v<T1,0UL> == DefaultMaxSize_v &&
6635  ( !IsSquare_v<T1> || MaxSize_v<T2,0UL> == DefaultMaxSize_v ) ) ||
6636  ( MaxSize_v<T2,1UL> == DefaultMaxSize_v &&
6637  ( !IsSquare_v<T2> || MaxSize_v<T1,1UL> == DefaultMaxSize_v ) ) ) > >
6638 {
6639  using ET1 = ElementType_t<T1>;
6640  using ET2 = ElementType_t<T2>;
6641 
6642  static constexpr bool SO = ( IsSparseMatrix_v<T1> ? StorageOrder_v<T2> : StorageOrder_v<T1> );
6643 
6644  using Type = DynamicMatrix< MultTrait_t<ET1,ET2>, SO >;
6645 };
6647 //*************************************************************************************************
6648 
6649 
6650 
6651 
6652 //=================================================================================================
6653 //
6654 // DIVTRAIT SPECIALIZATIONS
6655 //
6656 //=================================================================================================
6657 
6658 //*************************************************************************************************
6660 template< typename T1, typename T2 >
6661 struct DivTraitEval2< T1, T2
6662  , EnableIf_t< IsDenseMatrix_v<T1> &&
6663  IsNumeric_v<T2> &&
6664  ( Size_v<T1,0UL> == DefaultSize_v ) &&
6665  ( Size_v<T1,1UL> == DefaultSize_v ) &&
6666  ( MaxSize_v<T1,0UL> == DefaultMaxSize_v ) &&
6667  ( MaxSize_v<T1,1UL> == DefaultMaxSize_v ) > >
6668 {
6669  using ET1 = ElementType_t<T1>;
6670 
6671  using Type = DynamicMatrix< DivTrait_t<ET1,T2>, StorageOrder_v<T1> >;
6672 };
6674 //*************************************************************************************************
6675 
6676 
6677 
6678 
6679 //=================================================================================================
6680 //
6681 // MAPTRAIT SPECIALIZATIONS
6682 //
6683 //=================================================================================================
6684 
6685 //*************************************************************************************************
6687 template< typename T, typename OP >
6688 struct UnaryMapTraitEval2< T, OP
6689  , EnableIf_t< IsDenseMatrix_v<T> &&
6690  ( Size_v<T,0UL> == DefaultSize_v ||
6691  Size_v<T,1UL> == DefaultSize_v ) &&
6692  ( MaxSize_v<T,0UL> == DefaultMaxSize_v ||
6693  MaxSize_v<T,1UL> == DefaultMaxSize_v ) > >
6694 {
6695  using ET = ElementType_t<T>;
6696 
6697  using Type = DynamicMatrix< MapTrait_t<ET,OP>, StorageOrder_v<T> >;
6698 };
6700 //*************************************************************************************************
6701 
6702 
6703 //*************************************************************************************************
6705 template< typename T1, typename T2, typename OP >
6706 struct BinaryMapTraitEval2< T1, T2, OP
6707  , EnableIf_t< IsMatrix_v<T1> &&
6708  IsMatrix_v<T2> &&
6709  ( Size_v<T1,0UL> == DefaultSize_v ) &&
6710  ( Size_v<T2,0UL> == DefaultSize_v ) &&
6711  ( Size_v<T1,1UL> == DefaultSize_v ) &&
6712  ( Size_v<T2,1UL> == DefaultSize_v ) &&
6713  ( MaxSize_v<T1,0UL> == DefaultMaxSize_v ) &&
6714  ( MaxSize_v<T2,0UL> == DefaultMaxSize_v ) &&
6715  ( MaxSize_v<T1,1UL> == DefaultMaxSize_v ) &&
6716  ( MaxSize_v<T2,1UL> == DefaultMaxSize_v ) > >
6717 {
6718  using ET1 = ElementType_t<T1>;
6719  using ET2 = ElementType_t<T2>;
6720 
6721  static constexpr bool SO1 = StorageOrder_v<T1>;
6722  static constexpr bool SO2 = StorageOrder_v<T2>;
6723 
6724  static constexpr bool SO = ( IsDenseMatrix_v<T1> && IsDenseMatrix_v<T2>
6725  ? ( IsSymmetric_v<T1> ^ IsSymmetric_v<T2>
6726  ? ( IsSymmetric_v<T1>
6727  ? SO2
6728  : SO1 )
6729  : SO1 && SO2 )
6730  : ( IsDenseMatrix_v<T1>
6731  ? SO1
6732  : SO2 ) );
6733 
6734  using Type = DynamicMatrix< MapTrait_t<ET1,ET2,OP>, SO >;
6735 };
6737 //*************************************************************************************************
6738 
6739 
6740 
6741 
6742 //=================================================================================================
6743 //
6744 // EXPANDTRAIT SPECIALIZATIONS
6745 //
6746 //=================================================================================================
6747 
6748 //*************************************************************************************************
6750 template< typename T // Type to be expanded
6751  , size_t E > // Compile time expansion
6752 struct ExpandTraitEval2< T, E
6753  , EnableIf_t< IsDenseVector_v<T> &&
6754  ( ( E == inf ) ||
6755  ( ( Size_v<T,0UL> == DefaultSize_v ) &&
6756  ( MaxSize_v<T,0UL> == DefaultMaxSize_v ) ) ) > >
6757 {
6758  static constexpr bool TF = ( IsColumnVector_v<T> ? columnMajor : rowMajor );
6759 
6760  using Type = DynamicMatrix< ElementType_t<T>, TF >;
6761 };
6763 //*************************************************************************************************
6764 
6765 
6766 
6767 
6768 //=================================================================================================
6769 //
6770 // HIGHTYPE SPECIALIZATIONS
6771 //
6772 //=================================================================================================
6773 
6774 //*************************************************************************************************
6776 template< typename T1, bool SO, typename T2 >
6777 struct HighType< DynamicMatrix<T1,SO>, DynamicMatrix<T2,SO> >
6778 {
6779  using Type = DynamicMatrix< typename HighType<T1,T2>::Type, SO >;
6780 };
6782 //*************************************************************************************************
6783 
6784 
6785 
6786 
6787 //=================================================================================================
6788 //
6789 // LOWTYPE SPECIALIZATIONS
6790 //
6791 //=================================================================================================
6792 
6793 //*************************************************************************************************
6795 template< typename T1, bool SO, typename T2 >
6796 struct LowType< DynamicMatrix<T1,SO>, DynamicMatrix<T2,SO> >
6797 {
6798  using Type = DynamicMatrix< typename LowType<T1,T2>::Type, SO >;
6799 };
6801 //*************************************************************************************************
6802 
6803 
6804 
6805 
6806 //=================================================================================================
6807 //
6808 // SUBMATRIXTRAIT SPECIALIZATIONS
6809 //
6810 //=================================================================================================
6811 
6812 //*************************************************************************************************
6814 template< typename MT >
6815 struct SubmatrixTraitEval2< MT, inf, inf, inf, inf
6816  , EnableIf_t< IsDenseMatrix_v<MT> &&
6817  ( Size_v<MT,0UL> == DefaultSize_v ||
6818  Size_v<MT,1UL> == DefaultSize_v ) &&
6819  ( MaxSize_v<MT,0UL> == DefaultMaxSize_v ||
6820  MaxSize_v<MT,1UL> == DefaultMaxSize_v ) > >
6821 {
6822  using Type = DynamicMatrix< RemoveConst_t< ElementType_t<MT> >, StorageOrder_v<MT> >;
6823 };
6825 //*************************************************************************************************
6826 
6827 
6828 
6829 
6830 //=================================================================================================
6831 //
6832 // ROWSTRAIT SPECIALIZATIONS
6833 //
6834 //=================================================================================================
6835 
6836 //*************************************************************************************************
6838 template< typename MT, size_t M >
6839 struct RowsTraitEval2< MT, M
6840  , EnableIf_t< IsDenseMatrix_v<MT> &&
6841  ( M == 0UL || Size_v<MT,1UL> == DefaultSize_v ) &&
6842  ( M == 0UL || MaxSize_v<MT,1UL> == DefaultMaxSize_v ) > >
6843 {
6844  using Type = DynamicMatrix< RemoveConst_t< ElementType_t<MT> >, false >;
6845 };
6847 //*************************************************************************************************
6848 
6849 
6850 
6851 
6852 //=================================================================================================
6853 //
6854 // COLUMNSTRAIT SPECIALIZATIONS
6855 //
6856 //=================================================================================================
6857 
6858 //*************************************************************************************************
6860 template< typename MT, size_t N >
6861 struct ColumnsTraitEval2< MT, N
6862  , EnableIf_t< IsDenseMatrix_v<MT> &&
6863  ( N == 0UL || Size_v<MT,0UL> == DefaultSize_v ) &&
6864  ( N == 0UL || MaxSize_v<MT,0UL> == DefaultMaxSize_v ) > >
6865 {
6866  using Type = DynamicMatrix< RemoveConst_t< ElementType_t<MT> >, true >;
6867 };
6869 //*************************************************************************************************
6870 
6871 } // namespace blaze
6872 
6873 #endif
Constraint on the data type.
#define BLAZE_CONSTRAINT_MUST_NOT_BE_CONST(T)
Constraint on the data type.In case the given data type is a const-qualified type, a compilation error is created.
Definition: Const.h:79
#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
size_t n_
The current number of columns of the matrix.
Definition: DynamicMatrix.h:510
size_t addPadding(size_t value) const noexcept
Add the necessary amount of padding to the given value.
Definition: DynamicMatrix.h:1841
Header file for auxiliary alias declarations.
Headerfile for the generic min algorithm.
BLAZE_ALWAYS_INLINE void storeu(size_t i, size_t j, const SIMDType &value) noexcept
Unaligned store of a SIMD element of the matrix.
Definition: DynamicMatrix.h:2272
Header file for kernel specific block sizes.
Header file for the Schur product trait.
bool isAligned() const noexcept
Returns whether the matrix is properly aligned in memory.
Definition: DynamicMatrix.h:2066
void reserve(size_t elements)
Setting the minimum capacity of the matrix.
Definition: DynamicMatrix.h:1762
Header file for the nextMultiple shim.
#define BLAZE_USER_ASSERT(expr, msg)
Run time assertion macro for user checks.In case of an invalid run time expression, the program execution is terminated. The BLAZE_USER_ASSERT macro can be disabled by setting the BLAZE_USER_ASSERT flag to zero or by defining NDEBUG during the compilation.
Definition: Assert.h:117
Header file for the alignment flag values.
size_t rows() const noexcept
Returns the current number of rows of the matrix.
Definition: DynamicMatrix.h:1465
Header file for the UNUSED_PARAMETER function template.
Header file for the subtraction trait.
BLAZE_ALWAYS_INLINE SIMDType load(size_t i, size_t j) const noexcept
Load of a SIMD element of the matrix.
Definition: DynamicMatrix.h:2110
Header file for basic type definitions.
auto subAssign(const DenseMatrix< MT, SO > &rhs) -> DisableIf_t< VectorizedSubAssign_v< MT > >
Default implementation of the subtraction assignment of a row-major dense matrix. ...
Definition: DynamicMatrix.h:2750
constexpr bool HasSIMDSub_v
Auxiliary variable template for the HasSIMDSub type trait.The HasSIMDSub_v variable template provides...
Definition: HasSIMDSub.h:188
constexpr bool IsMatrix_v
Auxiliary variable template for the IsMatrix type trait.The IsMatrix_v variable template provides a c...
Definition: IsMatrix.h:139
Type *BLAZE_RESTRICT v_
The dynamically allocated matrix elements.
Definition: DynamicMatrix.h:513
BLAZE_ALWAYS_INLINE SIMDType loadu(size_t i, size_t j) const noexcept
Unaligned load of a SIMD element of the matrix.
Definition: DynamicMatrix.h:2173
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 IsSparseMatrix type trait.
DynamicMatrix & operator=(const Type &rhs)
Homogenous assignment to all matrix elements.
Definition: DynamicMatrix.h:1158
Efficient implementation of a compressed matrix.The CompressedMatrix class template is the represent...
Definition: CompressedMatrix.h:224
void resize(size_t m, size_t n, bool preserve=true)
Changing the size of the matrix.
Definition: DynamicMatrix.h:1685
Header file for the IsDiagonal type trait.
DynamicMatrix() noexcept
The default constructor for DynamicMatrix.
Definition: DynamicMatrix.h:551
Header file for the IsSame and IsStrictlySame type traits.
BLAZE_ALWAYS_INLINE const EnableIf_t< IsIntegral_v< T > &&HasSize_v< T, 1UL >, If_t< IsSigned_v< T >, SIMDint8, SIMDuint8 > > loadu(const T *address) noexcept
Loads a vector of 1-byte integral values.
Definition: Loadu.h:76
BLAZE_ALWAYS_INLINE void store(size_t i, size_t j, const SIMDType &value) noexcept
Store of a SIMD element of the matrix.
Definition: DynamicMatrix.h:2207
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
void reset(const DiagonalProxy< MT > &proxy)
Resetting the represented element to the default initial values.
Definition: DiagonalProxy.h:591
Type ElementType
Type of the matrix elements.
Definition: DynamicMatrix.h:230
size_t m_
The current number of rows of the compressed matrix.
Definition: CompressedMatrix.h:3289
Header file for the IsRowVector type trait.
typename SIMDTrait< T >::Type SIMDTrait_t
Auxiliary alias declaration for the SIMDTrait class template.The SIMDTrait_t alias declaration provid...
Definition: SIMDTrait.h:315
void ctranspose(Matrix< MT, SO > &matrix)
In-place conjugate transpose of the given matrix.
Definition: Matrix.h:851
const Type & ConstReference
Reference to a constant matrix value.
Definition: CompressedMatrix.h:3084
#define BLAZE_CONSTRAINT_MUST_NOT_BE_VOLATILE(T)
Constraint on the data type.In case the given data type is a volatile-qualified type, a compilation error is created.
Definition: Volatile.h:79
ConstIterator cend(size_t i) const noexcept
Returns an iterator just past the last element of row/column i.
Definition: DynamicMatrix.h:1134
Access proxy for sparse, matrices.The MatrixAccessProxy provides safe access to the elements of a no...
Definition: MatrixAccessProxy.h:101
BLAZE_ALWAYS_INLINE void cswap(T &a, T &b) noexcept(IsNumeric_v< T >)
Swapping two conjugated values/objects.
Definition: Conjugate.h:195
Header file for the reset shim.
Type & Reference
Reference to a non-constant matrix value.
Definition: DynamicMatrix.h:235
BoolConstant< true > TrueType
Type traits base class.The TrueType class is used as base class for type traits and value traits that...
Definition: TrueType.h:61
Element * Iterator
Iterator over non-constant elements.
Definition: CompressedMatrix.h:3085
Header file for memory allocation and deallocation functionality.
BLAZE_ALWAYS_INLINE EnableIf_t< IsIntegral_v< T1 > &&HasSize_v< T1, 1UL > > storeu(T1 *address, const SIMDi8< T2 > &value) noexcept
Unaligned store of a vector of 1-byte integral values.
Definition: Storeu.h:75
Header file for the extended initializer_list functionality.
System settings for performance optimizations.
Efficient implementation of a dynamic matrix.The DynamicMatrix class template is the representation ...
Definition: DynamicMatrix.h:220
constexpr void UNUSED_PARAMETER(const Args &...)
Suppression of unused parameter warnings.
Definition: Unused.h:81
Header file for the MaxSize type trait.
BLAZE_ALWAYS_INLINE void stream(size_t i, size_t j, const SIMDType &value) noexcept
Aligned, non-temporal store of a SIMD element of the matrix.
Definition: DynamicMatrix.h:2307
constexpr size_t columns(const Matrix< MT, SO > &matrix) noexcept
Returns the current number of columns of the matrix.
Definition: Matrix.h:514
constexpr bool rowMajor
Storage order flag for row-major matrices.
Definition: StorageOrder.h:71
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
bool canSMPAssign() const noexcept
Returns whether the matrix can be used in SMP assignments.
Definition: DynamicMatrix.h:2085
Constraint on the data type.
size_t capacity_
The current capacity of the pointer array.
Definition: CompressedMatrix.h:3291
Header file for the IsMatrix type trait.
~DynamicMatrix()
The destructor for DynamicMatrix.
Definition: DynamicMatrix.h:815
Header file for the SparseMatrix base class.
size_t spacing() const noexcept
Returns the spacing between the beginning of two rows/columns.
Definition: DynamicMatrix.h:1498
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
constexpr bool columnMajor
Storage order flag for column-major matrices.
Definition: StorageOrder.h:99
Headerfile for the generic max algorithm.
Header file for the DisableIf class template.
Header file for the LowType type trait.
Header file for the multiplication trait.
Header file for the IsStrictlyUpper type trait.
constexpr ptrdiff_t DefaultMaxSize_v
Default size of the MaxSize type trait.
Definition: MaxSize.h:72
constexpr bool IsSIMDCombinable_v
Auxiliary variable template for the IsSIMDCombinable type trait.The IsSIMDCombinable_v variable templ...
Definition: IsSIMDCombinable.h:137
Header file for the IsSymmetric type trait.
DynamicMatrix & ctranspose()
In-place conjugate transpose of the matrix.
Definition: DynamicMatrix.h:1903
Namespace of the Blaze C++ math library.
Definition: Blaze.h:58
#define BLAZE_ALWAYS_INLINE
Platform dependent setup of an enforced inline keyword.
Definition: Inline.h:85
decltype(auto) ctrans(const DenseMatrix< MT, SO > &dm)
Returns the conjugate transpose matrix of dm.
Definition: DMatMapExpr.h:1364
void swap(CompressedMatrix< Type, SO > &a, CompressedMatrix< Type, SO > &b) noexcept
Swapping the contents of two compressed matrices.
Definition: CompressedMatrix.h:5907
void shrinkToFit()
Requesting the removal of unused capacity.
Definition: DynamicMatrix.h:1800
bool isAliased(const Other *alias) const noexcept
Returns whether the matrix is aliased with the given address alias.
Definition: DynamicMatrix.h:2048
Header file for the IsShrinkable type trait.
constexpr bool HasSIMDMult_v
Auxiliary variable template for the HasSIMDMult type trait.The HasSIMDMult_v variable template provid...
Definition: HasSIMDMult.h:189
DynamicMatrix< NewType, SO > Other
The type of the other DynamicMatrix.
Definition: DynamicMatrix.h:249
Header file for all forward declarations of the math module.
#define BLAZE_CONSTRAINT_MUST_NOT_BE_POINTER_TYPE(T)
Constraint on the data type.In case the given data type T is not a pointer type, a compilation error ...
Definition: Pointer.h:79
Header file for the IsSMPAssignable type trait.
Type ElementType
Type of the compressed matrix elements.
Definition: CompressedMatrix.h:3080
Header file for the expand trait.
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
#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
Type * Pointer
Pointer to a non-constant matrix value.
Definition: DynamicMatrix.h:237
Header file for the HasSIMDAdd type trait.
Header file for the DenseMatrix base class.
Header file for the DenseIterator class template.
const Element * ConstIterator
Iterator over constant elements.
Definition: CompressedMatrix.h:3086
decltype(auto) inv(const DenseMatrix< MT, SO > &dm)
Calculation of the inverse of the given dense matrix.
Definition: DMatInvExpr.h:423
constexpr bool IsNumeric_v
Auxiliary variable template for the IsNumeric type trait.The IsNumeric_v variable template provides a...
Definition: IsNumeric.h:143
Header file for all SIMD functionality.
Constraint on the data type.
#define BLAZE_CONSTRAINT_MUST_NOT_BE_DIAGONAL_MATRIX_TYPE(T)
Constraint on the data type.In case the given data type T is a diagonal matrix type, a compilation error is created.
Definition: Diagonal.h:79
static constexpr bool smpAssignable
Compilation flag for SMP assignments.
Definition: DynamicMatrix.h:275
Header file for the IsLower type trait.
Header file for the IsAligned type trait.
constexpr bool IsDenseVector_v
Auxiliary variable template for the IsDenseVector type trait.The IsDenseVector_v variable template pr...
Definition: IsDenseVector.h:139
void extend(size_t m, size_t n, bool preserve=true)
Extending the size of the matrix.
Definition: DynamicMatrix.h:1744
BLAZE_ALWAYS_INLINE EnableIf_t< IsIntegral_v< T1 > &&HasSize_v< T1, 1UL > > storea(T1 *address, const SIMDi8< T2 > &value) noexcept
Aligned store of a vector of 1-byte integral values.
Definition: Storea.h:78
#define BLAZE_RESTRICT
Platform dependent setup of the restrict keyword.
Definition: Restrict.h:81
Header file for the default storage order for all vectors of the Blaze library.
#define BLAZE_CONSTRAINT_MUST_BE_VECTORIZABLE_TYPE(T)
Constraint on the data type.In case the given data type T is not a vectorizable data type...
Definition: Vectorizable.h:61
void reset()
Reset to the default initial values.
Definition: DynamicMatrix.h:1598
auto addAssign(const DenseMatrix< MT, SO > &rhs) -> DisableIf_t< VectorizedAddAssign_v< MT > >
Default implementation of the addition assignment of a row-major dense matrix.
Definition: DynamicMatrix.h:2536
decltype(auto) elements(Vector< VT, TF > &vector, REAs... args)
Creating a view on a selection of elements of the given vector.
Definition: Elements.h:135
SIMDTrait_t< ElementType > SIMDType
SIMD type of the matrix elements.
Definition: DynamicMatrix.h:231
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
void resize(Matrix< MT, SO > &matrix, size_t rows, size_t columns, bool preserve=true)
Changing the size of the matrix.
Definition: Matrix.h:738
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
size_t columns() const noexcept
Returns the current number of columns of the matrix.
Definition: DynamicMatrix.h:1479
Header file for the IsDenseMatrix type trait.
Header file for the EnableIf class template.
Header file for the IsStrictlyLower type trait.
void clear(const DiagonalProxy< MT > &proxy)
Clearing the represented element.
Definition: DiagonalProxy.h:611
Header file for the IsPadded type trait.
const Type & ConstReference
Reference to a constant matrix value.
Definition: DynamicMatrix.h:236
BLAZE_ALWAYS_INLINE void storea(size_t i, size_t j, const SIMDType &value) noexcept
Aligned store of a SIMD element of the matrix.
Definition: DynamicMatrix.h:2236
Header file for the IsVectorizable type trait.
Pointer data() noexcept
Low-level data access to the matrix elements.
Definition: DynamicMatrix.h:943
Reference operator()(size_t i, size_t j) noexcept
2D-access to the matrix elements.
Definition: DynamicMatrix.h:843
Header file for the conjugate shim.
Header file for the IsNumeric type trait.
Header file for the HasConstDataAccess type trait.
size_t nn_
The alignment adjusted number of columns.
Definition: DynamicMatrix.h:511
Header file for the RemoveConst type trait.
Header file for the IsSIMDCombinable 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:79
Header file for the HasSIMDMult type trait.
BLAZE_ALWAYS_INLINE void conjugate(T &a) noexcept(IsNumeric_v< T >)
In-place conjugation of the given value/object.
Definition: Conjugate.h:120
Header file for run time assertion macros.
auto schurAssign(const DenseMatrix< MT, SO > &rhs) -> DisableIf_t< VectorizedSchurAssign_v< MT > >
Default implementation of the Schur product assignment of a row-major dense matrix.
Definition: DynamicMatrix.h:2964
Iterator begin(size_t i) noexcept
Returns an iterator to the first element of row/column i.
Definition: DynamicMatrix.h:1024
Header file for the addition trait.
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
void clear()
Clearing the matrix.
Definition: DynamicMatrix.h:1642
Header file for the division trait.
Header file for the submatrix trait.
ConstIterator cbegin(size_t i) const noexcept
Returns an iterator to the first element of row/column i.
Definition: DynamicMatrix.h:1068
Constraint on the data type.
Header file for the IsContiguous type trait.
Header file for the columns trait.
Headerfile for the generic transfer algorithm.
size_t m_
The current number of rows of the matrix.
Definition: DynamicMatrix.h:509
static constexpr size_t SIMDSIZE
The number of elements packed within a single SIMD element.
Definition: DynamicMatrix.h:427
SIMD characteristics of data types.The SIMDTrait class template provides the SIMD characteristics of ...
Definition: SIMDTrait.h:295
Header file for the cache size of the target architecture.
#define BLAZE_CONSTRAINT_MUST_NOT_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:79
Header file for the isDefault shim.
void swap(DiagonalMatrix< MT, SO, DF > &a, DiagonalMatrix< MT, SO, DF > &b) noexcept
Swapping the contents of two matrices.
Definition: DiagonalMatrix.h:281
System settings for the restrict keyword.
bool canAlias(const Other *alias) const noexcept
Returns whether the matrix can alias with the given address alias.
Definition: DynamicMatrix.h:2028
constexpr size_t size(const Matrix< MT, SO > &matrix) noexcept
Returns the total number of elements of the matrix.
Definition: Matrix.h:530
Constraint on the data type.
auto assign(const DenseMatrix< MT, SO > &rhs) -> DisableIf_t< VectorizedAssign_v< MT > >
Default implementation of the assignment of a row-major dense matrix.
Definition: DynamicMatrix.h:2338
Base class for matrices.The Matrix class is a base class for all dense and sparse matrix classes with...
Definition: Forward.h:109
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
Constraint on the data type.
void swap(DynamicMatrix &m) noexcept
Swapping the contents of two matrices.
Definition: DynamicMatrix.h:1817
Constraint on the data type.
Header file for the HasSIMDSub type trait.
constexpr bool IsDenseMatrix_v
Auxiliary variable template for the IsDenseMatrix type trait.The IsDenseMatrix_v variable template pr...
Definition: IsDenseMatrix.h:139
Header file for the HasMutableDataAccess type trait.
DenseIterator< Type, usePadding > Iterator
Iterator over non-constant elements.
Definition: DynamicMatrix.h:240
constexpr ptrdiff_t DefaultSize_v
Default size of the Size type trait.
Definition: Size.h:72
size_t nonZeros() const
Returns the total number of non-zero elements in the matrix.
Definition: DynamicMatrix.h:1548
IntegralConstant< bool, B > BoolConstant
Generic wrapper for a compile time constant boolean value.The BoolConstant class template represents ...
Definition: IntegralConstant.h:101
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
constexpr bool IsDiagonal_v
Auxiliary variable template for the IsDiagonal type trait.The IsDiagonal_v variable template provides...
Definition: IsDiagonal.h:148
BLAZE_ALWAYS_INLINE const EnableIf_t< IsIntegral_v< T > &&HasSize_v< T, 1UL >, If_t< IsSigned_v< T >, SIMDint8, SIMDuint8 > > loada(const T *address) noexcept
Loads a vector of 1-byte integral values.
Definition: Loada.h:79
Header file for the IsDenseVector type trait.
Implementation of a generic iterator for dense vectors and matrices.The DenseIterator represents a ge...
Definition: DenseIterator.h:58
Header file for the rows trait.
typename T::ConstIterator ConstIterator_t
Alias declaration for nested ConstIterator type definitions.The ConstIterator_t alias declaration pro...
Definition: Aliases.h:110
BLAZE_ALWAYS_INLINE EnableIf_t< IsIntegral_v< T1 > &&HasSize_v< T1, 1UL > > stream(T1 *address, const SIMDi8< T2 > &value) noexcept
Aligned, non-temporal store of a vector of 1-byte integral values.
Definition: Stream.h:74
BLAZE_ALWAYS_INLINE bool checkAlignment(const T *address)
Checks the alignment of the given address.
Definition: AlignmentCheck.h:68
const Type & ReturnType
Return type for expression template evaluations.
Definition: CompressedMatrix.h:3081
decltype(auto) trans(const DenseMatrix< MT, SO > &dm)
Calculation of the transpose of the given dense matrix.
Definition: DMatTransExpr.h:765
size_t n_
The current number of columns of the compressed matrix.
Definition: CompressedMatrix.h:3290
BLAZE_ALWAYS_INLINE SIMDType loada(size_t i, size_t j) const noexcept
Aligned load of a SIMD element of the matrix.
Definition: DynamicMatrix.h:2138
Iterator end(size_t i) noexcept
Returns an iterator just past the last element of row/column i.
Definition: DynamicMatrix.h:1090
DynamicMatrix< Type, SO > This
Type of this DynamicMatrix instance.
Definition: DynamicMatrix.h:225
DynamicMatrix< Type, SO > Other
The type of the other DynamicMatrix.
Definition: DynamicMatrix.h:259
EnableIf_t< IsBuiltin_v< T > > deallocate(T *address) noexcept
Deallocation of memory for built-in data types.
Definition: Memory.h:224
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 default transpose flag for all vectors of the Blaze library.
Initializer list type of the Blaze library.
bool isIntact() const noexcept
Returns whether the invariants of the dynamic matrix are intact.
Definition: DynamicMatrix.h:1988
Header file for the alignment check function.
constexpr bool HasSIMDAdd_v
Auxiliary variable template for the HasSIMDAdd type trait.The HasSIMDAdd_v variable template provides...
Definition: HasSIMDAdd.h:188
size_t capacity_
The maximum capacity of the matrix.
Definition: DynamicMatrix.h:512
Header file for the StorageOrder type trait.
Header file for the IntegralConstant class template.
Resize mechanism to obtain a DynamicMatrix with different fixed dimensions.
Definition: DynamicMatrix.h:258
constexpr Infinity inf
Global Infinity instance.The blaze::inf instance can be used wherever a built-in data type is expecte...
Definition: Infinity.h:1080
Header file for the map trait.
bool isIntact(const DiagonalMatrix< MT, SO, DF > &m)
Returns whether the invariants of the given diagonal matrix are intact.
Definition: DiagonalMatrix.h:263
Rebind mechanism to obtain a DynamicMatrix with different data/element type.
Definition: DynamicMatrix.h:248
DenseIterator< const Type, usePadding > ConstIterator
Iterator over constant elements.
Definition: DynamicMatrix.h:241
bool isDefault(const DiagonalProxy< MT > &proxy)
Returns whether the represented element is in default state.
Definition: DiagonalProxy.h:631
Rebind mechanism to obtain a CompressedMatrix with different data/element type.
Definition: CompressedMatrix.h:3093
Header file for the IsUpper type trait.
typename DisableIf< Condition, T >::Type DisableIf_t
Auxiliary type for the DisableIf class template.The DisableIf_t alias declaration provides a convenie...
Definition: DisableIf.h:138
size_t capacity() const noexcept
Returns the maximum capacity of the matrix.
Definition: DynamicMatrix.h:1512
Header file for the IsColumnVector type trait.
OutputIterator transfer(InputIterator first, InputIterator last, OutputIterator dest)
Transfers the elements from the given source range to the destination range.
Definition: Transfer.h:70
Reference at(size_t i, size_t j)
Checked access to the matrix elements.
Definition: DynamicMatrix.h:888
Header file for the IsResizable type trait.
System settings for the inline keywords.
Header file for the Size type trait.
EnableIf_t< IsBuiltin_v< T >, T *> allocate(size_t size)
Aligned array allocation for built-in data types.
Definition: Memory.h:156
Header file for the thresholds for matrix/vector and matrix/matrix multiplications.
static constexpr bool simdEnabled
Compilation flag for SIMD optimization.
Definition: DynamicMatrix.h:269
#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
const Type & ReturnType
Return type for expression template evaluations.
Definition: DynamicMatrix.h:232
DynamicMatrix & transpose()
In-place transpose of the matrix.
Definition: DynamicMatrix.h:1865
constexpr size_t determineColumns(initializer_list< initializer_list< Type > > list) noexcept
Determines the maximum number of columns specified by the given initializer list. ...
Definition: InitializerList.h:108
Header file for the HighType type trait.
Header file for the TrueType type/value trait base class.
Header file for the clear shim.
const Type * ConstPointer
Pointer to a constant matrix value.
Definition: DynamicMatrix.h:238
void transpose(Matrix< MT, SO > &matrix)
In-place transpose of the given matrix.
Definition: Matrix.h:825