Sparse.h
Go to the documentation of this file.
1 //=================================================================================================
33 //=================================================================================================
34 
35 #ifndef _BLAZE_MATH_VIEWS_COLUMN_SPARSE_H_
36 #define _BLAZE_MATH_VIEWS_COLUMN_SPARSE_H_
37 
38 
39 //*************************************************************************************************
40 // Includes
41 //*************************************************************************************************
42 
43 #include <iterator>
44 #include <blaze/math/Aliases.h>
56 #include <blaze/math/Exception.h>
60 #include <blaze/math/shims/Reset.h>
80 #include <blaze/util/Assert.h>
83 #include <blaze/util/DisableIf.h>
84 #include <blaze/util/EnableIf.h>
85 #include <blaze/util/mpl/If.h>
86 #include <blaze/util/Types.h>
92 #include <blaze/util/Unused.h>
93 
94 
95 namespace blaze {
96 
97 //=================================================================================================
98 //
99 // CLASS TEMPLATE SPECIALIZATION FOR COLUMN-MAJOR SPARSE MATRICES
100 //
101 //=================================================================================================
102 
103 //*************************************************************************************************
111 template< typename MT // Type of the sparse matrix
112  , bool SF > // Symmetry flag
113 class Column<MT,true,false,SF>
114  : public View< SparseVector< Column<MT,true,false,SF>, false > >
115 {
116  private:
117  //**Type definitions****************************************************************************
119  using Operand = If_< IsExpression<MT>, MT, MT& >;
120  //**********************************************************************************************
121 
122  public:
123  //**Type definitions****************************************************************************
124  using This = Column<MT,true,false,SF>;
125  using BaseType = SparseVector<This,false>;
126  using ResultType = ColumnTrait_<MT>;
127  using TransposeType = TransposeType_<ResultType>;
128  using ElementType = ElementType_<MT>;
129  using ReturnType = ReturnType_<MT>;
130  using CompositeType = const Column&;
131 
133  using ConstReference = ConstReference_<MT>;
134 
136  using Reference = If_< IsConst<MT>, ConstReference, Reference_<MT> >;
137 
139  using ConstIterator = ConstIterator_<MT>;
140 
142  using Iterator = If_< IsConst<MT>, ConstIterator, Iterator_<MT> >;
143  //**********************************************************************************************
144 
145  //**Compilation flags***************************************************************************
147  enum : bool { smpAssignable = false };
148  //**********************************************************************************************
149 
150  //**Constructors********************************************************************************
153  explicit inline Column( Operand matrix, size_t index );
154  // No explicitly declared copy constructor.
156  //**********************************************************************************************
157 
158  //**Destructor**********************************************************************************
159  // No explicitly declared destructor.
160  //**********************************************************************************************
161 
162  //**Data access functions***********************************************************************
165  inline Reference operator[]( size_t index );
166  inline ConstReference operator[]( size_t index ) const;
167  inline Reference at( size_t index );
168  inline ConstReference at( size_t index ) const;
169  inline Iterator begin ();
170  inline ConstIterator begin () const;
171  inline ConstIterator cbegin() const;
172  inline Iterator end ();
173  inline ConstIterator end () const;
174  inline ConstIterator cend () const;
176  //**********************************************************************************************
177 
178  //**Assignment operators************************************************************************
181  inline Column& operator=( const Column& rhs );
182 
183  template< typename VT > inline Column& operator= ( const DenseVector<VT,false>& rhs );
184  template< typename VT > inline Column& operator= ( const SparseVector<VT,false>& rhs );
185  template< typename VT > inline Column& operator+=( const DenseVector<VT,false>& rhs );
186  template< typename VT > inline Column& operator+=( const SparseVector<VT,false>& rhs );
187  template< typename VT > inline Column& operator-=( const DenseVector<VT,false>& rhs );
188  template< typename VT > inline Column& operator-=( const SparseVector<VT,false>& rhs );
189  template< typename VT > inline Column& operator*=( const Vector<VT,false>& rhs );
190  template< typename VT > inline Column& operator/=( const DenseVector<VT,false>& rhs );
191  template< typename VT > inline Column& operator%=( const Vector<VT,false>& rhs );
192 
193  template< typename Other >
194  inline EnableIf_< IsNumeric<Other>, Column >& operator*=( Other rhs );
195 
196  template< typename Other >
197  inline EnableIf_<IsNumeric<Other>, Column >& operator/=( Other rhs );
199  //**********************************************************************************************
200 
201  //**Utility functions***************************************************************************
204  inline Operand operand() const noexcept;
205  inline size_t column() const noexcept;
206  inline size_t size() const noexcept;
207  inline size_t capacity() const noexcept;
208  inline size_t nonZeros() const;
209  inline void reset();
210  inline void reserve( size_t n );
212  //**********************************************************************************************
213 
214  //**Insertion functions*************************************************************************
217  inline Iterator set ( size_t index, const ElementType& value );
218  inline Iterator insert( size_t index, const ElementType& value );
219  inline void append( size_t index, const ElementType& value, bool check=false );
221  //**********************************************************************************************
222 
223  //**Erase functions*****************************************************************************
226  inline void erase( size_t index );
227  inline Iterator erase( Iterator pos );
228  inline Iterator erase( Iterator first, Iterator last );
229 
230  template< typename Pred, typename = DisableIf_< IsIntegral<Pred> > >
231  inline void erase( Pred predicate );
232 
233  template< typename Pred >
234  inline void erase( Iterator first, Iterator last, Pred predicate );
236  //**********************************************************************************************
237 
238  //**Lookup functions****************************************************************************
241  inline Iterator find ( size_t index );
242  inline ConstIterator find ( size_t index ) const;
243  inline Iterator lowerBound( size_t index );
244  inline ConstIterator lowerBound( size_t index ) const;
245  inline Iterator upperBound( size_t index );
246  inline ConstIterator upperBound( size_t index ) const;
248  //**********************************************************************************************
249 
250  //**Numeric functions***************************************************************************
253  template< typename Other > inline Column& scale( const Other& scalar );
255  //**********************************************************************************************
256 
257  //**Expression template evaluation functions****************************************************
260  template< typename Other > inline bool canAlias ( const Other* alias ) const noexcept;
261  template< typename Other > inline bool isAliased( const Other* alias ) const noexcept;
262 
263  template< typename VT > inline void assign ( const DenseVector <VT,false>& rhs );
264  template< typename VT > inline void assign ( const SparseVector<VT,false>& rhs );
265  template< typename VT > inline void addAssign( const DenseVector <VT,false>& rhs );
266  template< typename VT > inline void addAssign( const SparseVector<VT,false>& rhs );
267  template< typename VT > inline void subAssign( const DenseVector <VT,false>& rhs );
268  template< typename VT > inline void subAssign( const SparseVector<VT,false>& rhs );
270  //**********************************************************************************************
271 
272  private:
273  //**Utility functions***************************************************************************
276  inline size_t extendCapacity() const noexcept;
278  //**********************************************************************************************
279 
280  //**Member variables****************************************************************************
283  Operand matrix_;
284  const size_t col_;
285 
286  //**********************************************************************************************
287 
288  //**Compile time checks*************************************************************************
295  //**********************************************************************************************
296 };
298 //*************************************************************************************************
299 
300 
301 
302 
303 //=================================================================================================
304 //
305 // CONSTRUCTOR
306 //
307 //=================================================================================================
308 
309 //*************************************************************************************************
317 template< typename MT // Type of the sparse matrix
318  , bool SF > // Symmetry flag
319 inline Column<MT,true,false,SF>::Column( Operand matrix, size_t index )
320  : matrix_( matrix ) // The sparse matrix containing the column
321  , col_ ( index ) // The index of the column in the matrix
322 {
323  if( matrix_.columns() <= index ) {
324  BLAZE_THROW_INVALID_ARGUMENT( "Invalid column access index" );
325  }
326 }
328 //*************************************************************************************************
329 
330 
331 
332 
333 //=================================================================================================
334 //
335 // DATA ACCESS FUNCTIONS
336 //
337 //=================================================================================================
338 
339 //*************************************************************************************************
349 template< typename MT // Type of the sparse matrix
350  , bool SF > // Symmetry flag
352  Column<MT,true,false,SF>::operator[]( size_t index )
353 {
354  BLAZE_USER_ASSERT( index < size(), "Invalid column access index" );
355  return matrix_(index,col_);
356 }
358 //*************************************************************************************************
359 
360 
361 //*************************************************************************************************
371 template< typename MT // Type of the sparse matrix
372  , bool SF > // Symmetry flag
374  Column<MT,true,false,SF>::operator[]( size_t index ) const
375 {
376  BLAZE_USER_ASSERT( index < size(), "Invalid column access index" );
377  return const_cast<const MT&>( matrix_ )(index,col_);
378 }
380 //*************************************************************************************************
381 
382 
383 //*************************************************************************************************
394 template< typename MT // Type of the sparse matrix
395  , bool SF > // Symmetry flag
397  Column<MT,true,false,SF>::at( size_t index )
398 {
399  if( index >= size() ) {
400  BLAZE_THROW_OUT_OF_RANGE( "Invalid column access index" );
401  }
402  return (*this)[index];
403 }
405 //*************************************************************************************************
406 
407 
408 //*************************************************************************************************
419 template< typename MT // Type of the sparse matrix
420  , bool SF > // Symmetry flag
422  Column<MT,true,false,SF>::at( size_t index ) const
423 {
424  if( index >= size() ) {
425  BLAZE_THROW_OUT_OF_RANGE( "Invalid column access index" );
426  }
427  return (*this)[index];
428 }
430 //*************************************************************************************************
431 
432 
433 //*************************************************************************************************
441 template< typename MT // Type of the sparse matrix
442  , bool SF > // Symmetry flag
444 {
445  return matrix_.begin( col_ );
446 }
448 //*************************************************************************************************
449 
450 
451 //*************************************************************************************************
459 template< typename MT // Type of the sparse matrix
460  , bool SF > // Symmetry flag
462 {
463  return matrix_.cbegin( col_ );
464 }
466 //*************************************************************************************************
467 
468 
469 //*************************************************************************************************
477 template< typename MT // Type of the sparse matrix
478  , bool SF > // Symmetry flag
480 {
481  return matrix_.cbegin( col_ );
482 }
484 //*************************************************************************************************
485 
486 
487 //*************************************************************************************************
495 template< typename MT // Type of the sparse matrix
496  , bool SF > // Symmetry flag
498 {
499  return matrix_.end( col_ );
500 }
502 //*************************************************************************************************
503 
504 
505 //*************************************************************************************************
513 template< typename MT // Type of the sparse matrix
514  , bool SF > // Symmetry flag
516 {
517  return matrix_.cend( col_ );
518 }
520 //*************************************************************************************************
521 
522 
523 //*************************************************************************************************
531 template< typename MT // Type of the sparse matrix
532  , bool SF > // Symmetry flag
534 {
535  return matrix_.cend( col_ );
536 }
538 //*************************************************************************************************
539 
540 
541 
542 
543 //=================================================================================================
544 //
545 // ASSIGNMENT OPERATORS
546 //
547 //=================================================================================================
548 
549 //*************************************************************************************************
563 template< typename MT // Type of the sparse matrix
564  , bool SF > // Symmetry flag
565 inline Column<MT,true,false,SF>& Column<MT,true,false,SF>::operator=( const Column& rhs )
566 {
567  using blaze::assign;
568 
572 
573  if( this == &rhs || ( &matrix_ == &rhs.matrix_ && col_ == rhs.col_ ) )
574  return *this;
575 
576  if( size() != rhs.size() ) {
577  BLAZE_THROW_INVALID_ARGUMENT( "Column sizes do not match" );
578  }
579 
580  if( !tryAssign( matrix_, rhs, 0UL, col_ ) ) {
581  BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted matrix" );
582  }
583 
584  decltype(auto) left( derestrict( *this ) );
585 
586  if( rhs.canAlias( &matrix_ ) ) {
587  const ResultType tmp( rhs );
588  left.reset();
589  left.reserve( tmp.nonZeros() );
590  assign( left, tmp );
591  }
592  else {
593  left.reset();
594  left.reserve( rhs.nonZeros() );
595  assign( left, rhs );
596  }
597 
598  BLAZE_INTERNAL_ASSERT( isIntact( matrix_ ), "Invariant violation detected" );
599 
600  return *this;
601 }
603 //*************************************************************************************************
604 
605 
606 //*************************************************************************************************
620 template< typename MT // Type of the sparse matrix
621  , bool SF > // Symmetry flag
622 template< typename VT > // Type of the right-hand side dense vector
623 inline Column<MT,true,false,SF>& Column<MT,true,false,SF>::operator=( const DenseVector<VT,false>& rhs )
624 {
625  using blaze::assign;
626 
627  BLAZE_CONSTRAINT_MUST_BE_DENSE_VECTOR_TYPE ( ResultType_<VT> );
630 
631  if( size() != (~rhs).size() ) {
632  BLAZE_THROW_INVALID_ARGUMENT( "Vector sizes do not match" );
633  }
634 
635  using Right = If_< IsRestricted<MT>, CompositeType_<VT>, const VT& >;
636  Right right( ~rhs );
637 
638  if( !tryAssign( matrix_, right, 0UL, col_ ) ) {
639  BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted matrix" );
640  }
641 
642  decltype(auto) left( derestrict( *this ) );
643 
644  if( IsReference<Right>::value && right.canAlias( &matrix_ ) ) {
645  const ResultType_<VT> tmp( right );
646  left.reset();
647  assign( left, tmp );
648  }
649  else {
650  left.reset();
651  assign( left, right );
652  }
653 
654  BLAZE_INTERNAL_ASSERT( isIntact( matrix_ ), "Invariant violation detected" );
655 
656  return *this;
657 }
659 //*************************************************************************************************
660 
661 
662 //*************************************************************************************************
676 template< typename MT // Type of the sparse matrix
677  , bool SF > // Symmetry flag
678 template< typename VT > // Type of the right-hand side sparse vector
679 inline Column<MT,true,false,SF>& Column<MT,true,false,SF>::operator=( const SparseVector<VT,false>& rhs )
680 {
681  using blaze::assign;
682 
686 
687  if( size() != (~rhs).size() ) {
688  BLAZE_THROW_INVALID_ARGUMENT( "Vector sizes do not match" );
689  }
690 
691  using Right = If_< IsRestricted<MT>, CompositeType_<VT>, const VT& >;
692  Right right( ~rhs );
693 
694  if( !tryAssign( matrix_, right, 0UL, col_ ) ) {
695  BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted matrix" );
696  }
697 
698  decltype(auto) left( derestrict( *this ) );
699 
700  if( IsReference<Right>::value && right.canAlias( &matrix_ ) ) {
701  const ResultType_<VT> tmp( right );
702  left.reset();
703  left.reserve( tmp.nonZeros() );
704  assign( left, tmp );
705  }
706  else {
707  left.reset();
708  left.reserve( right.nonZeros() );
709  assign( left, right );
710  }
711 
712  BLAZE_INTERNAL_ASSERT( isIntact( matrix_ ), "Invariant violation detected" );
713 
714  return *this;
715 }
717 //*************************************************************************************************
718 
719 
720 //*************************************************************************************************
734 template< typename MT // Type of the sparse matrix
735  , bool SF > // Symmetry flag
736 template< typename VT > // Type of the right-hand side dense vector
737 inline Column<MT,true,false,SF>& Column<MT,true,false,SF>::operator+=( const DenseVector<VT,false>& rhs )
738 {
739  using blaze::assign;
740 
744  BLAZE_CONSTRAINT_MUST_BE_DENSE_VECTOR_TYPE ( ResultType_<VT> );
747 
748  using AddType = AddTrait_< ResultType, ResultType_<VT> >;
749 
753 
754  if( size() != (~rhs).size() ) {
755  BLAZE_THROW_INVALID_ARGUMENT( "Vector sizes do not match" );
756  }
757 
758  const AddType tmp( *this + (~rhs) );
759 
760  if( !tryAssign( matrix_, tmp, 0UL, col_ ) ) {
761  BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted matrix" );
762  }
763 
764  decltype(auto) left( derestrict( *this ) );
765 
766  left.reset();
767  assign( left, tmp );
768 
769  BLAZE_INTERNAL_ASSERT( isIntact( matrix_ ), "Invariant violation detected" );
770 
771  return *this;
772 }
774 //*************************************************************************************************
775 
776 
777 //*************************************************************************************************
791 template< typename MT // Type of the sparse matrix
792  , bool SF > // Symmetry flag
793 template< typename VT > // Type of the right-hand side sparse vector
794 inline Column<MT,true,false,SF>& Column<MT,true,false,SF>::operator+=( const SparseVector<VT,false>& rhs )
795 {
796  using blaze::assign;
797 
804 
805  using AddType = AddTrait_< ResultType, ResultType_<VT> >;
806 
810 
811  if( size() != (~rhs).size() ) {
812  BLAZE_THROW_INVALID_ARGUMENT( "Vector sizes do not match" );
813  }
814 
815  const AddType tmp( *this + (~rhs) );
816 
817  if( !tryAssign( matrix_, tmp, 0UL, col_ ) ) {
818  BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted matrix" );
819  }
820 
821  decltype(auto) left( derestrict( *this ) );
822 
823  left.reset();
824  left.reserve( tmp.nonZeros() );
825  assign( left, tmp );
826 
827  BLAZE_INTERNAL_ASSERT( isIntact( matrix_ ), "Invariant violation detected" );
828 
829  return *this;
830 }
832 //*************************************************************************************************
833 
834 
835 //*************************************************************************************************
850 template< typename MT // Type of the sparse matrix
851  , bool SF > // Symmetry flag
852 template< typename VT > // Type of the right-hand side dense vector
853 inline Column<MT,true,false,SF>& Column<MT,true,false,SF>::operator-=( const DenseVector<VT,false>& rhs )
854 {
855  using blaze::assign;
856 
860  BLAZE_CONSTRAINT_MUST_BE_DENSE_VECTOR_TYPE ( ResultType_<VT> );
863 
864  using SubType = SubTrait_< ResultType, ResultType_<VT> >;
865 
869 
870  if( size() != (~rhs).size() ) {
871  BLAZE_THROW_INVALID_ARGUMENT( "Vector sizes do not match" );
872  }
873 
874  const SubType tmp( *this - (~rhs) );
875 
876  if( !tryAssign( matrix_, tmp, 0UL, col_ ) ) {
877  BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted matrix" );
878  }
879 
880  decltype(auto) left( derestrict( *this ) );
881 
882  left.reset();
883  assign( left, tmp );
884 
885  BLAZE_INTERNAL_ASSERT( isIntact( matrix_ ), "Invariant violation detected" );
886 
887  return *this;
888 }
890 //*************************************************************************************************
891 
892 
893 //*************************************************************************************************
908 template< typename MT // Type of the sparse matrix
909  , bool SF > // Symmetry flag
910 template< typename VT > // Type of the right-hand side sparse vector
911 inline Column<MT,true,false,SF>& Column<MT,true,false,SF>::operator-=( const SparseVector<VT,false>& rhs )
912 {
913  using blaze::assign;
914 
921 
922  using SubType = SubTrait_< ResultType, ResultType_<VT> >;
923 
927 
928  if( size() != (~rhs).size() ) {
929  BLAZE_THROW_INVALID_ARGUMENT( "Vector sizes do not match" );
930  }
931 
932  const SubType tmp( *this - (~rhs) );
933 
934  if( !tryAssign( matrix_, tmp, 0UL, col_ ) ) {
935  BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted matrix" );
936  }
937 
938  decltype(auto) left( derestrict( *this ) );
939 
940  left.reset();
941  left.reserve( tmp.nonZeros() );
942  assign( left, tmp );
943 
944  BLAZE_INTERNAL_ASSERT( isIntact( matrix_ ), "Invariant violation detected" );
945 
946  return *this;
947 }
949 //*************************************************************************************************
950 
951 
952 //*************************************************************************************************
965 template< typename MT // Type of the sparse matrix
966  , bool SF > // Symmetry flag
967 template< typename VT > // Type of the right-hand side vector
968 inline Column<MT,true,false,SF>& Column<MT,true,false,SF>::operator*=( const Vector<VT,false>& rhs )
969 {
970  using blaze::assign;
971 
977 
978  using MultType = MultTrait_< ResultType, ResultType_<VT> >;
979 
982 
983  if( size() != (~rhs).size() ) {
984  BLAZE_THROW_INVALID_ARGUMENT( "Vector sizes do not match" );
985  }
986 
987  const MultType tmp( *this * (~rhs) );
988 
989  if( !tryAssign( matrix_, tmp, 0UL, col_ ) ) {
990  BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted matrix" );
991  }
992 
993  decltype(auto) left( derestrict( *this ) );
994 
995  left.reset();
996  assign( left, tmp );
997 
998  BLAZE_INTERNAL_ASSERT( isIntact( matrix_ ), "Invariant violation detected" );
999 
1000  return *this;
1001 }
1003 //*************************************************************************************************
1004 
1005 
1006 //*************************************************************************************************
1018 template< typename MT // Type of the sparse matrix
1019  , bool SF > // Symmetry flag
1020 template< typename VT > // Type of the right-hand side vector
1021 inline Column<MT,true,false,SF>& Column<MT,true,false,SF>::operator/=( const DenseVector<VT,false>& rhs )
1022 {
1023  using blaze::assign;
1024 
1028  BLAZE_CONSTRAINT_MUST_BE_DENSE_VECTOR_TYPE ( ResultType_<VT> );
1029  BLAZE_CONSTRAINT_MUST_BE_COLUMN_VECTOR_TYPE ( ResultType_<VT> );
1031 
1032  using DivType = DivTrait_< ResultType, ResultType_<VT> >;
1033 
1037 
1038  if( size() != (~rhs).size() ) {
1039  BLAZE_THROW_INVALID_ARGUMENT( "Vector sizes do not match" );
1040  }
1041 
1042  const DivType tmp( *this / (~rhs) );
1043 
1044  if( !tryAssign( matrix_, tmp, 0UL, col_ ) ) {
1045  BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted matrix" );
1046  }
1047 
1048  decltype(auto) left( derestrict( *this ) );
1049 
1050  left.reset();
1051  assign( left, tmp );
1052 
1053  BLAZE_INTERNAL_ASSERT( isIntact( matrix_ ), "Invariant violation detected" );
1054 
1055  return *this;
1056 }
1058 //*************************************************************************************************
1059 
1060 
1061 //*************************************************************************************************
1074 template< typename MT // Type of the sparse matrix
1075  , bool SF > // Symmetry flag
1076 template< typename VT > // Type of the right-hand side vector
1077 inline Column<MT,true,false,SF>& Column<MT,true,false,SF>::operator%=( const Vector<VT,false>& rhs )
1078 {
1079  using blaze::assign;
1080 
1081  BLAZE_CONSTRAINT_MUST_BE_COLUMN_VECTOR_TYPE ( ResultType_<VT> );
1083 
1084  using CrossType = CrossTrait_< ResultType, ResultType_<VT> >;
1085 
1089 
1090  if( size() != 3UL || (~rhs).size() != 3UL ) {
1091  BLAZE_THROW_INVALID_ARGUMENT( "Invalid vector size for cross product" );
1092  }
1093 
1094  const CrossType tmp( *this % (~rhs) );
1095 
1096  if( !tryAssign( matrix_, tmp, 0UL, col_ ) ) {
1097  BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted matrix" );
1098  }
1099 
1100  decltype(auto) left( derestrict( *this ) );
1101 
1102  left.reset();
1103  assign( left, tmp );
1104 
1105  BLAZE_INTERNAL_ASSERT( isIntact( matrix_ ), "Invariant violation detected" );
1106 
1107  return *this;
1108 }
1110 //*************************************************************************************************
1111 
1112 
1113 //*************************************************************************************************
1128 template< typename MT // Type of the sparse matrix
1129  , bool SF > // Symmetry flag
1130 template< typename Other > // Data type of the right-hand side scalar
1131 inline EnableIf_<IsNumeric<Other>, Column<MT,true,false,SF> >&
1132  Column<MT,true,false,SF>::operator*=( Other rhs )
1133 {
1135 
1136  for( Iterator element=begin(); element!=end(); ++element )
1137  element->value() *= rhs;
1138  return *this;
1139 }
1141 //*************************************************************************************************
1142 
1143 
1144 //*************************************************************************************************
1162 template< typename MT // Type of the sparse matrix
1163  , bool SF > // Symmetry flag
1164 template< typename Other > // Data type of the right-hand side scalar
1165 inline EnableIf_<IsNumeric<Other>, Column<MT,true,false,SF> >&
1167 {
1169 
1170  BLAZE_USER_ASSERT( rhs != Other(0), "Division by zero detected" );
1171 
1172  using DT = DivTrait_<ElementType,Other>;
1173  using Tmp = If_< IsNumeric<DT>, DT, Other >;
1174 
1175  // Depending on the two involved data types, an integer division is applied or a
1176  // floating point division is selected.
1177  if( IsNumeric<DT>::value && IsFloatingPoint<DT>::value ) {
1178  const Tmp tmp( Tmp(1)/static_cast<Tmp>( rhs ) );
1179  for( Iterator element=begin(); element!=end(); ++element )
1180  element->value() *= tmp;
1181  }
1182  else {
1183  for( Iterator element=begin(); element!=end(); ++element )
1184  element->value() /= rhs;
1185  }
1186 
1187  return *this;
1188 }
1190 //*************************************************************************************************
1191 
1192 
1193 
1194 
1195 //=================================================================================================
1196 //
1197 // UTILITY FUNCTIONS
1198 //
1199 //=================================================================================================
1200 
1201 //*************************************************************************************************
1207 template< typename MT // Type of the sparse matrix
1208  , bool SF > // Symmetry flag
1209 inline typename Column<MT,true,false,SF>::Operand
1210  Column<MT,true,false,SF>::operand() const noexcept
1211 {
1212  return matrix_;
1213 }
1215 //*************************************************************************************************
1216 
1217 
1218 //*************************************************************************************************
1224 template< typename MT // Type of the sparse matrix
1225  , bool SF > // Symmetry flag
1226 inline size_t Column<MT,true,false,SF>::column() const noexcept
1227 {
1228  return col_;
1229 }
1231 //*************************************************************************************************
1232 
1233 
1234 //*************************************************************************************************
1240 template< typename MT // Type of the sparse matrix
1241  , bool SF > // Symmetry flag
1242 inline size_t Column<MT,true,false,SF>::size() const noexcept
1243 {
1244  return matrix_.rows();
1245 }
1247 //*************************************************************************************************
1248 
1249 
1250 //*************************************************************************************************
1256 template< typename MT // Type of the sparse matrix
1257  , bool SF > // Symmetry flag
1258 inline size_t Column<MT,true,false,SF>::capacity() const noexcept
1259 {
1260  return matrix_.capacity( col_ );
1261 }
1263 //*************************************************************************************************
1264 
1265 
1266 //*************************************************************************************************
1275 template< typename MT // Type of the sparse matrix
1276  , bool SF > // Symmetry flag
1277 inline size_t Column<MT,true,false,SF>::nonZeros() const
1278 {
1279  return matrix_.nonZeros( col_ );
1280 }
1282 //*************************************************************************************************
1283 
1284 
1285 //*************************************************************************************************
1291 template< typename MT // Type of the sparse matrix
1292  , bool SF > // Symmetry flag
1293 inline void Column<MT,true,false,SF>::reset()
1294 {
1295  matrix_.reset( col_ );
1296 }
1298 //*************************************************************************************************
1299 
1300 
1301 //*************************************************************************************************
1311 template< typename MT // Type of the sparse matrix
1312  , bool SF > // Symmetry flag
1313 void Column<MT,true,false,SF>::reserve( size_t n )
1314 {
1315  matrix_.reserve( col_, n );
1316 }
1318 //*************************************************************************************************
1319 
1320 
1321 //*************************************************************************************************
1330 template< typename MT // Type of the sparse matrix
1331  , bool SF > // Symmetry flag
1332 inline size_t Column<MT,true,false,SF>::extendCapacity() const noexcept
1333 {
1334  using blaze::max;
1335  using blaze::min;
1336 
1337  size_t nonzeros( 2UL*capacity()+1UL );
1338  nonzeros = max( nonzeros, 7UL );
1339  nonzeros = min( nonzeros, size() );
1340 
1341  BLAZE_INTERNAL_ASSERT( nonzeros > capacity(), "Invalid capacity value" );
1342 
1343  return nonzeros;
1344 }
1346 //*************************************************************************************************
1347 
1348 
1349 
1350 
1351 //=================================================================================================
1352 //
1353 // INSERTION FUNCTIONS
1354 //
1355 //=================================================================================================
1356 
1357 //*************************************************************************************************
1369 template< typename MT // Type of the sparse matrix
1370  , bool SF > // Symmetry flag
1371 inline typename Column<MT,true,false,SF>::Iterator
1372  Column<MT,true,false,SF>::set( size_t index, const ElementType& value )
1373 {
1374  return matrix_.set( index, col_, value );
1375 }
1377 //*************************************************************************************************
1378 
1379 
1380 //*************************************************************************************************
1393 template< typename MT // Type of the sparse matrix
1394  , bool SF > // Symmetry flag
1395 inline typename Column<MT,true,false,SF>::Iterator
1396  Column<MT,true,false,SF>::insert( size_t index, const ElementType& value )
1397 {
1398  return matrix_.insert( index, col_, value );
1399 }
1401 //*************************************************************************************************
1402 
1403 
1404 //*************************************************************************************************
1429 template< typename MT // Type of the sparse matrix
1430  , bool SF > // Symmetry flag
1431 inline void Column<MT,true,false,SF>::append( size_t index, const ElementType& value, bool check )
1432 {
1433  matrix_.append( index, col_, value, check );
1434 }
1436 //*************************************************************************************************
1437 
1438 
1439 
1440 
1441 //=================================================================================================
1442 //
1443 // ERASE FUNCTIONS
1444 //
1445 //=================================================================================================
1446 
1447 //*************************************************************************************************
1456 template< typename MT // Type of the sparse matrix
1457  , bool SF > // Symmetry flag
1458 inline void Column<MT,true,false,SF>::erase( size_t index )
1459 {
1460  matrix_.erase( index, col_ );
1461 }
1463 //*************************************************************************************************
1464 
1465 
1466 //*************************************************************************************************
1475 template< typename MT // Type of the sparse matrix
1476  , bool SF > // Symmetry flag
1477 inline typename Column<MT,true,false,SF>::Iterator Column<MT,true,false,SF>::erase( Iterator pos )
1478 {
1479  return matrix_.erase( col_, pos );
1480 }
1482 //*************************************************************************************************
1483 
1484 
1485 //*************************************************************************************************
1495 template< typename MT // Type of the sparse matrix
1496  , bool SF > // Symmetry flag
1497 inline typename Column<MT,true,false,SF>::Iterator
1498  Column<MT,true,false,SF>::erase( Iterator first, Iterator last )
1499 {
1500  return matrix_.erase( col_, first, last );
1501 }
1503 //*************************************************************************************************
1504 
1505 
1506 //*************************************************************************************************
1529 template< typename MT // Type of the sparse matrix
1530  , bool SF > // Symmetry flag
1531 template< typename Pred // Type of the unary predicate
1532  , typename > // Type restriction on the unary predicate
1533 inline void Column<MT,true,false,SF>::erase( Pred predicate )
1534 {
1535  matrix_.erase( col_, begin(), end(), predicate );
1536 }
1538 //*************************************************************************************************
1539 
1540 
1541 //*************************************************************************************************
1566 template< typename MT // Type of the sparse matrix
1567  , bool SF > // Symmetry flag
1568 template< typename Pred > // Type of the unary predicate
1569 inline void Column<MT,true,false,SF>::erase( Iterator first, Iterator last, Pred predicate )
1570 {
1571  matrix_.erase( col_, first, last, predicate );
1572 }
1574 //*************************************************************************************************
1575 
1576 
1577 
1578 
1579 //=================================================================================================
1580 //
1581 // LOOKUP FUNCTIONS
1582 //
1583 //=================================================================================================
1584 
1585 //*************************************************************************************************
1599 template< typename MT // Type of the sparse matrix
1600  , bool SF > // Symmetry flag
1601 inline typename Column<MT,true,false,SF>::Iterator Column<MT,true,false,SF>::find( size_t index )
1602 {
1603  return matrix_.find( index, col_ );
1604 }
1606 //*************************************************************************************************
1607 
1608 
1609 //*************************************************************************************************
1623 template< typename MT // Type of the sparse matrix
1624  , bool SF > // Symmetry flag
1626  Column<MT,true,false,SF>::find( size_t index ) const
1627 {
1628  return matrix_.find( index, col_ );
1629 }
1631 //*************************************************************************************************
1632 
1633 
1634 //*************************************************************************************************
1647 template< typename MT // Type of the sparse matrix
1648  , bool SF > // Symmetry flag
1649 inline typename Column<MT,true,false,SF>::Iterator Column<MT,true,false,SF>::lowerBound( size_t index )
1650 {
1651  return matrix_.lowerBound( index, col_ );
1652 }
1654 //*************************************************************************************************
1655 
1656 
1657 //*************************************************************************************************
1670 template< typename MT // Type of the sparse matrix
1671  , bool SF > // Symmetry flag
1673  Column<MT,true,false,SF>::lowerBound( size_t index ) const
1674 {
1675  return matrix_.lowerBound( index, col_ );
1676 }
1678 //*************************************************************************************************
1679 
1680 
1681 //*************************************************************************************************
1694 template< typename MT // Type of the sparse matrix
1695  , bool SF > // Symmetry flag
1696 inline typename Column<MT,true,false,SF>::Iterator Column<MT,true,false,SF>::upperBound( size_t index )
1697 {
1698  return matrix_.upperBound( index, col_ );
1699 }
1701 //*************************************************************************************************
1702 
1703 
1704 //*************************************************************************************************
1717 template< typename MT // Type of the sparse matrix
1718  , bool SF > // Symmetry flag
1720  Column<MT,true,false,SF>::upperBound( size_t index ) const
1721 {
1722  return matrix_.upperBound( index, col_ );
1723 }
1725 //*************************************************************************************************
1726 
1727 
1728 
1729 
1730 //=================================================================================================
1731 //
1732 // NUMERIC FUNCTIONS
1733 //
1734 //=================================================================================================
1735 
1736 //*************************************************************************************************
1749 template< typename MT // Type of the sparse matrix
1750  , bool SF > // Symmetry flag
1751 template< typename Other > // Data type of the scalar value
1752 inline Column<MT,true,false,SF>& Column<MT,true,false,SF>::scale( const Other& scalar )
1753 {
1755 
1756  for( Iterator element=begin(); element!=end(); ++element )
1757  element->value() *= scalar;
1758  return *this;
1759 }
1761 //*************************************************************************************************
1762 
1763 
1764 
1765 
1766 //=================================================================================================
1767 //
1768 // EXPRESSION TEMPLATE EVALUATION FUNCTIONS
1769 //
1770 //=================================================================================================
1771 
1772 //*************************************************************************************************
1783 template< typename MT // Type of the sparse matrix
1784  , bool SF > // Symmetry flag
1785 template< typename Other > // Data type of the foreign expression
1786 inline bool Column<MT,true,false,SF>::canAlias( const Other* alias ) const noexcept
1787 {
1788  return matrix_.isAliased( alias );
1789 }
1791 //*************************************************************************************************
1792 
1793 
1794 //*************************************************************************************************
1805 template< typename MT // Type of the sparse matrix
1806  , bool SF > // Symmetry flag
1807 template< typename Other > // Data type of the foreign expression
1808 inline bool Column<MT,true,false,SF>::isAliased( const Other* alias ) const noexcept
1809 {
1810  return matrix_.isAliased( alias );
1811 }
1813 //*************************************************************************************************
1814 
1815 
1816 //*************************************************************************************************
1828 template< typename MT // Type of the sparse matrix
1829  , bool SF > // Symmetry flag
1830 template< typename VT > // Type of the right-hand side dense vector
1831 inline void Column<MT,true,false,SF>::assign( const DenseVector<VT,false>& rhs )
1832 {
1833  BLAZE_INTERNAL_ASSERT( size() == (~rhs).size(), "Invalid vector sizes" );
1834  BLAZE_INTERNAL_ASSERT( nonZeros() == 0UL, "Invalid non-zero elements detected" );
1835 
1836  for( size_t i=0UL; i<size(); ++i )
1837  {
1838  if( matrix_.nonZeros( col_ ) == matrix_.capacity( col_ ) )
1839  matrix_.reserve( col_, extendCapacity() );
1840 
1841  matrix_.append( i, col_, (~rhs)[i], true );
1842  }
1843 }
1845 //*************************************************************************************************
1846 
1847 
1848 //*************************************************************************************************
1860 template< typename MT // Type of the sparse matrix
1861  , bool SF > // Symmetry flag
1862 template< typename VT > // Type of the right-hand side sparse vector
1863 inline void Column<MT,true,false,SF>::assign( const SparseVector<VT,false>& rhs )
1864 {
1865  BLAZE_INTERNAL_ASSERT( size() == (~rhs).size(), "Invalid vector sizes" );
1866  BLAZE_INTERNAL_ASSERT( nonZeros() == 0UL, "Invalid non-zero elements detected" );
1867 
1868  for( ConstIterator_<VT> element=(~rhs).begin(); element!=(~rhs).end(); ++element ) {
1869  matrix_.append( element->index(), col_, element->value(), true );
1870  }
1871 }
1873 //*************************************************************************************************
1874 
1875 
1876 //*************************************************************************************************
1888 template< typename MT // Type of the sparse matrix
1889  , bool SF > // Symmetry flag
1890 template< typename VT > // Type of the right-hand side dense vector
1891 inline void Column<MT,true,false,SF>::addAssign( const DenseVector<VT,false>& rhs )
1892 {
1893  using AddType = AddTrait_< ResultType, ResultType_<VT> >;
1894 
1898 
1899  BLAZE_INTERNAL_ASSERT( size() == (~rhs).size(), "Invalid vector sizes" );
1900 
1901  const AddType tmp( serial( *this + (~rhs) ) );
1902  matrix_.reset( col_ );
1903  assign( tmp );
1904 }
1906 //*************************************************************************************************
1907 
1908 
1909 //*************************************************************************************************
1921 template< typename MT // Type of the sparse matrix
1922  , bool SF > // Symmetry flag
1923 template< typename VT > // Type of the right-hand side sparse vector
1924 inline void Column<MT,true,false,SF>::addAssign( const SparseVector<VT,false>& rhs )
1925 {
1926  using AddType = AddTrait_< ResultType, ResultType_<VT> >;
1927 
1931 
1932  BLAZE_INTERNAL_ASSERT( size() == (~rhs).size(), "Invalid vector sizes" );
1933 
1934  const AddType tmp( serial( *this + (~rhs) ) );
1935  matrix_.reset( col_ );
1936  matrix_.reserve( col_, tmp.nonZeros() );
1937  assign( tmp );
1938 }
1940 //*************************************************************************************************
1941 
1942 
1943 //*************************************************************************************************
1955 template< typename MT // Type of the sparse matrix
1956  , bool SF > // Symmetry flag
1957 template< typename VT > // Type of the right-hand side dense vector
1958 inline void Column<MT,true,false,SF>::subAssign( const DenseVector<VT,false>& rhs )
1959 {
1960  using SubType = SubTrait_< ResultType, ResultType_<VT> >;
1961 
1965 
1966  BLAZE_INTERNAL_ASSERT( size() == (~rhs).size(), "Invalid vector sizes" );
1967 
1968  const SubType tmp( serial( *this - (~rhs) ) );
1969  matrix_.reset( col_ );
1970  assign( tmp );
1971 }
1973 //*************************************************************************************************
1974 
1975 
1976 //*************************************************************************************************
1988 template< typename MT // Type of the sparse matrix
1989  , bool SF > // Symmetry flag
1990 template< typename VT > // Type of the right-hand side sparse vector
1991 inline void Column<MT,true,false,SF>::subAssign( const SparseVector<VT,false>& rhs )
1992 {
1993  using SubType = SubTrait_< ResultType, ResultType_<VT> >;
1994 
1998 
1999  BLAZE_INTERNAL_ASSERT( size() == (~rhs).size(), "Invalid vector sizes" );
2000 
2001  const SubType tmp( serial( *this - (~rhs) ) );
2002  matrix_.reset( col_ );
2003  matrix_.reserve( col_, tmp.nonZeros() );
2004  assign( tmp );
2005 }
2007 //*************************************************************************************************
2008 
2009 
2010 
2011 
2012 
2013 
2014 
2015 
2016 //=================================================================================================
2017 //
2018 // CLASS TEMPLATE SPECIALIZATION FOR GENERAL ROW-MAJOR SPARSE MATRICES
2019 //
2020 //=================================================================================================
2021 
2022 //*************************************************************************************************
2030 template< typename MT > // Type of the sparse matrix
2031 class Column<MT,false,false,false>
2032  : public View< SparseVector< Column<MT,false,false,false>, false > >
2033 {
2034  private:
2035  //**Type definitions****************************************************************************
2037  using Operand = If_< IsExpression<MT>, MT, MT& >;
2038  //**********************************************************************************************
2039 
2040  public:
2041  //**Type definitions****************************************************************************
2042  using This = Column<MT,false,false,false>;
2043  using BaseType = SparseVector<This,false>;
2044  using ResultType = ColumnTrait_<MT>;
2045  using TransposeType = TransposeType_<ResultType>;
2046  using ElementType = ElementType_<MT>;
2047  using ReturnType = ReturnType_<MT>;
2048  using CompositeType = const Column&;
2049 
2051  using ConstReference = ConstReference_<MT>;
2052 
2054  using Reference = If_< IsConst<MT>, ConstReference, Reference_<MT> >;
2055  //**********************************************************************************************
2056 
2057  //**ColumnElement class definition**************************************************************
2060  template< typename MatrixType // Type of the sparse matrix
2061  , typename IteratorType > // Type of the sparse matrix iterator
2062  class ColumnElement
2063  : private SparseElement
2064  {
2065  public:
2066  //**Constructor******************************************************************************
2072  inline ColumnElement( IteratorType pos, size_t row )
2073  : pos_( pos ) // Iterator to the current position within the sparse column
2074  , row_( row ) // Index of the according row
2075  {}
2076  //*******************************************************************************************
2077 
2078  //**Assignment operator**********************************************************************
2084  template< typename T > inline ColumnElement& operator=( const T& v ) {
2085  *pos_ = v;
2086  return *this;
2087  }
2088  //*******************************************************************************************
2089 
2090  //**Addition assignment operator*************************************************************
2096  template< typename T > inline ColumnElement& operator+=( const T& v ) {
2097  *pos_ += v;
2098  return *this;
2099  }
2100  //*******************************************************************************************
2101 
2102  //**Subtraction assignment operator**********************************************************
2108  template< typename T > inline ColumnElement& operator-=( const T& v ) {
2109  *pos_ -= v;
2110  return *this;
2111  }
2112  //*******************************************************************************************
2113 
2114  //**Multiplication assignment operator*******************************************************
2120  template< typename T > inline ColumnElement& operator*=( const T& v ) {
2121  *pos_ *= v;
2122  return *this;
2123  }
2124  //*******************************************************************************************
2125 
2126  //**Division assignment operator*************************************************************
2132  template< typename T > inline ColumnElement& operator/=( const T& v ) {
2133  *pos_ /= v;
2134  return *this;
2135  }
2136  //*******************************************************************************************
2137 
2138  //**Element access operator******************************************************************
2143  inline const ColumnElement* operator->() const {
2144  return this;
2145  }
2146  //*******************************************************************************************
2147 
2148  //**Value function***************************************************************************
2153  inline decltype(auto) value() const {
2154  return pos_->value();
2155  }
2156  //*******************************************************************************************
2157 
2158  //**Index function***************************************************************************
2163  inline size_t index() const {
2164  return row_;
2165  }
2166  //*******************************************************************************************
2167 
2168  private:
2169  //**Member variables*************************************************************************
2170  IteratorType pos_;
2171  size_t row_;
2172  //*******************************************************************************************
2173  };
2174  //**********************************************************************************************
2175 
2176  //**ColumnIterator class definition*************************************************************
2179  template< typename MatrixType // Type of the sparse matrix
2180  , typename IteratorType > // Type of the sparse matrix iterator
2181  class ColumnIterator
2182  {
2183  public:
2184  //**Type definitions*************************************************************************
2185  using IteratorCategory = std::forward_iterator_tag;
2186  using ValueType = ColumnElement<MatrixType,IteratorType>;
2187  using PointerType = ValueType;
2188  using ReferenceType = ValueType;
2189  using DifferenceType = ptrdiff_t;
2190 
2191  // STL iterator requirements
2192  using iterator_category = IteratorCategory;
2193  using value_type = ValueType;
2194  using pointer = PointerType;
2195  using reference = ReferenceType;
2196  using difference_type = DifferenceType;
2197  //*******************************************************************************************
2198 
2199  //**Constructor******************************************************************************
2202  inline ColumnIterator()
2203  : matrix_( nullptr ) // The sparse matrix containing the column.
2204  , row_ ( 0UL ) // The current row index.
2205  , column_( 0UL ) // The current column index.
2206  , pos_ () // Iterator to the current sparse element.
2207  {}
2208  //*******************************************************************************************
2209 
2210  //**Constructor******************************************************************************
2217  inline ColumnIterator( MatrixType& matrix, size_t row, size_t column )
2218  : matrix_( &matrix ) // The sparse matrix containing the column.
2219  , row_ ( row ) // The current row index.
2220  , column_( column ) // The current column index.
2221  , pos_ () // Iterator to the current sparse element.
2222  {
2223  for( ; row_<matrix_->rows(); ++row_ ) {
2224  pos_ = matrix_->find( row_, column_ );
2225  if( pos_ != matrix_->end( row_ ) ) break;
2226  }
2227  }
2228  //*******************************************************************************************
2229 
2230  //**Constructor******************************************************************************
2238  inline ColumnIterator( MatrixType& matrix, size_t row, size_t column, IteratorType pos )
2239  : matrix_( &matrix ) // The sparse matrix containing the column.
2240  , row_ ( row ) // The current row index.
2241  , column_( column ) // The current column index.
2242  , pos_ ( pos ) // Iterator to the current sparse element.
2243  {
2244  BLAZE_INTERNAL_ASSERT( matrix.find( row, column ) == pos, "Invalid initial iterator position" );
2245  }
2246  //*******************************************************************************************
2247 
2248  //**Constructor******************************************************************************
2253  template< typename MatrixType2, typename IteratorType2 >
2254  inline ColumnIterator( const ColumnIterator<MatrixType2,IteratorType2>& it )
2255  : matrix_( it.matrix_ ) // The sparse matrix containing the column.
2256  , row_ ( it.row_ ) // The current row index.
2257  , column_( it.column_ ) // The current column index.
2258  , pos_ ( it.pos_ ) // Iterator to the current sparse element.
2259  {}
2260  //*******************************************************************************************
2261 
2262  //**Prefix increment operator****************************************************************
2267  inline ColumnIterator& operator++() {
2268  ++row_;
2269  for( ; row_<matrix_->rows(); ++row_ ) {
2270  pos_ = matrix_->find( row_, column_ );
2271  if( pos_ != matrix_->end( row_ ) ) break;
2272  }
2273 
2274  return *this;
2275  }
2276  //*******************************************************************************************
2277 
2278  //**Postfix increment operator***************************************************************
2283  inline const ColumnIterator operator++( int ) {
2284  const ColumnIterator tmp( *this );
2285  ++(*this);
2286  return tmp;
2287  }
2288  //*******************************************************************************************
2289 
2290  //**Element access operator******************************************************************
2295  inline ReferenceType operator*() const {
2296  return ReferenceType( pos_, row_ );
2297  }
2298  //*******************************************************************************************
2299 
2300  //**Element access operator******************************************************************
2305  inline PointerType operator->() const {
2306  return PointerType( pos_, row_ );
2307  }
2308  //*******************************************************************************************
2309 
2310  //**Equality operator************************************************************************
2316  template< typename MatrixType2, typename IteratorType2 >
2317  inline bool operator==( const ColumnIterator<MatrixType2,IteratorType2>& rhs ) const {
2318  return ( matrix_ == rhs.matrix_ ) && ( row_ == rhs.row_ ) && ( column_ == rhs.column_ );
2319  }
2320  //*******************************************************************************************
2321 
2322  //**Inequality operator**********************************************************************
2328  template< typename MatrixType2, typename IteratorType2 >
2329  inline bool operator!=( const ColumnIterator<MatrixType2,IteratorType2>& rhs ) const {
2330  return !( *this == rhs );
2331  }
2332  //*******************************************************************************************
2333 
2334  //**Subtraction operator*********************************************************************
2340  inline DifferenceType operator-( const ColumnIterator& rhs ) const {
2341  size_t counter( 0UL );
2342  for( size_t i=rhs.row_; i<row_; ++i ) {
2343  if( matrix_->find( i, column_ ) != matrix_->end( i ) )
2344  ++counter;
2345  }
2346  return counter;
2347  }
2348  //*******************************************************************************************
2349 
2350  private:
2351  //**Member variables*************************************************************************
2352  MatrixType* matrix_;
2353  size_t row_;
2354  size_t column_;
2355  IteratorType pos_;
2356  //*******************************************************************************************
2357 
2358  //**Friend declarations**********************************************************************
2359  template< typename MatrixType2, typename IteratorType2 > friend class ColumnIterator;
2360  template< typename MT2, bool SO2, bool DF2, bool SF2 > friend class Column;
2361  //*******************************************************************************************
2362  };
2363  //**********************************************************************************************
2364 
2365  //**Type definitions****************************************************************************
2367  using ConstIterator = ColumnIterator< const MT, ConstIterator_<MT> >;
2368 
2370  using Iterator = If_< IsConst<MT>, ConstIterator, ColumnIterator< MT, Iterator_<MT> > >;
2371  //**********************************************************************************************
2372 
2373  //**Compilation flags***************************************************************************
2375  enum : bool { smpAssignable = false };
2376  //**********************************************************************************************
2377 
2378  //**Constructors********************************************************************************
2381  explicit inline Column( Operand matrix, size_t index );
2382  // No explicitly declared copy constructor.
2384  //**********************************************************************************************
2385 
2386  //**Destructor**********************************************************************************
2387  // No explicitly declared destructor.
2388  //**********************************************************************************************
2389 
2390  //**Data access functions***********************************************************************
2393  inline Reference operator[]( size_t index );
2394  inline ConstReference operator[]( size_t index ) const;
2395  inline Reference at( size_t index );
2396  inline ConstReference at( size_t index ) const;
2397  inline Iterator begin ();
2398  inline ConstIterator begin () const;
2399  inline ConstIterator cbegin() const;
2400  inline Iterator end ();
2401  inline ConstIterator end () const;
2402  inline ConstIterator cend () const;
2404  //**********************************************************************************************
2405 
2406  //**Assignment operators************************************************************************
2409  inline Column& operator= ( const Column& rhs );
2410  template< typename VT > inline Column& operator= ( const Vector<VT,false>& rhs );
2411  template< typename VT > inline Column& operator+=( const Vector<VT,false>& rhs );
2412  template< typename VT > inline Column& operator-=( const Vector<VT,false>& rhs );
2413  template< typename VT > inline Column& operator*=( const Vector<VT,false>& rhs );
2414  template< typename VT > inline Column& operator/=( const DenseVector<VT,false>& rhs );
2415  template< typename VT > inline Column& operator%=( const Vector<VT,false>& rhs );
2416 
2417  template< typename Other >
2418  inline EnableIf_<IsNumeric<Other>, Column >& operator*=( Other rhs );
2419 
2420  template< typename Other >
2421  inline EnableIf_<IsNumeric<Other>, Column >& operator/=( Other rhs );
2423  //**********************************************************************************************
2424 
2425  //**Utility functions***************************************************************************
2428  inline Operand operand() const noexcept;
2429  inline size_t column() const noexcept;
2430  inline size_t size() const;
2431  inline size_t capacity() const;
2432  inline size_t nonZeros() const;
2433  inline void reset();
2434  inline void reserve( size_t n );
2436  //**********************************************************************************************
2437 
2438  //**Insertion functions*************************************************************************
2441  inline Iterator set ( size_t index, const ElementType& value );
2442  inline Iterator insert( size_t index, const ElementType& value );
2443  inline void append( size_t index, const ElementType& value, bool check=false );
2445  //**********************************************************************************************
2446 
2447  //**Erase functions*****************************************************************************
2450  inline void erase( size_t index );
2451  inline Iterator erase( Iterator pos );
2452  inline Iterator erase( Iterator first, Iterator last );
2453 
2454  template< typename Pred, typename = DisableIf_< IsIntegral<Pred> > >
2455  inline void erase( Pred predicate );
2456 
2457  template< typename Pred >
2458  inline void erase( Iterator first, Iterator last, Pred predicate );
2460  //**********************************************************************************************
2461 
2462  //**Lookup functions****************************************************************************
2465  inline Iterator find ( size_t index );
2466  inline ConstIterator find ( size_t index ) const;
2467  inline Iterator lowerBound( size_t index );
2468  inline ConstIterator lowerBound( size_t index ) const;
2469  inline Iterator upperBound( size_t index );
2470  inline ConstIterator upperBound( size_t index ) const;
2472  //**********************************************************************************************
2473 
2474  //**Numeric functions***************************************************************************
2477  template< typename Other > inline Column& scale( const Other& scalar );
2479  //**********************************************************************************************
2480 
2481  //**Expression template evaluation functions****************************************************
2484  template< typename Other > inline bool canAlias ( const Other* alias ) const;
2485  template< typename Other > inline bool isAliased( const Other* alias ) const;
2486 
2487  template< typename VT > inline void assign ( const DenseVector <VT,false>& rhs );
2488  template< typename VT > inline void assign ( const SparseVector<VT,false>& rhs );
2489  template< typename VT > inline void addAssign( const Vector<VT,false>& rhs );
2490  template< typename VT > inline void subAssign( const Vector<VT,false>& rhs );
2492  //**********************************************************************************************
2493 
2494  private:
2495  //**Member variables****************************************************************************
2498  Operand matrix_;
2499  const size_t col_;
2500 
2501  //**********************************************************************************************
2502 
2503  //**Compile time checks*************************************************************************
2511  //**********************************************************************************************
2512 };
2514 //*************************************************************************************************
2515 
2516 
2517 
2518 
2519 //=================================================================================================
2520 //
2521 // CONSTRUCTOR
2522 //
2523 //=================================================================================================
2524 
2525 //*************************************************************************************************
2533 template< typename MT > // Type of the sparse matrix
2534 inline Column<MT,false,false,false>::Column( Operand matrix, size_t index )
2535  : matrix_( matrix ) // The sparse matrix containing the column
2536  , col_ ( index ) // The index of the column in the matrix
2537 {
2538  if( matrix_.columns() <= index ) {
2539  BLAZE_THROW_INVALID_ARGUMENT( "Invalid column access index" );
2540  }
2541 }
2543 //*************************************************************************************************
2544 
2545 
2546 
2547 
2548 //=================================================================================================
2549 //
2550 // DATA ACCESS FUNCTIONS
2551 //
2552 //=================================================================================================
2553 
2554 //*************************************************************************************************
2564 template< typename MT > // Type of the sparse matrix
2566  Column<MT,false,false,false>::operator[]( size_t index )
2567 {
2568  BLAZE_USER_ASSERT( index < size(), "Invalid column access index" );
2569  return matrix_(index,col_);
2570 }
2572 //*************************************************************************************************
2573 
2574 
2575 //*************************************************************************************************
2585 template< typename MT > // Type of the sparse matrix
2587  Column<MT,false,false,false>::operator[]( size_t index ) const
2588 {
2589  BLAZE_USER_ASSERT( index < size(), "Invalid column access index" );
2590  return const_cast<const MT&>( matrix_ )(index,col_);
2591 }
2593 //*************************************************************************************************
2594 
2595 
2596 //*************************************************************************************************
2607 template< typename MT > // Type of the sparse matrix
2609  Column<MT,false,false,false>::at( size_t index )
2610 {
2611  if( index >= size() ) {
2612  BLAZE_THROW_OUT_OF_RANGE( "Invalid column access index" );
2613  }
2614  return (*this)[index];
2615 }
2617 //*************************************************************************************************
2618 
2619 
2620 //*************************************************************************************************
2631 template< typename MT > // Type of the sparse matrix
2633  Column<MT,false,false,false>::at( size_t index ) const
2634 {
2635  if( index >= size() ) {
2636  BLAZE_THROW_OUT_OF_RANGE( "Invalid column access index" );
2637  }
2638  return (*this)[index];
2639 }
2641 //*************************************************************************************************
2642 
2643 
2644 //*************************************************************************************************
2652 template< typename MT > // Type of the sparse matrix
2654 {
2655  return Iterator( matrix_, 0UL, col_ );
2656 }
2658 //*************************************************************************************************
2659 
2660 
2661 //*************************************************************************************************
2669 template< typename MT > // Type of the sparse matrix
2672 {
2673  return ConstIterator( matrix_, 0UL, col_ );
2674 }
2676 //*************************************************************************************************
2677 
2678 
2679 //*************************************************************************************************
2687 template< typename MT > // Type of the sparse matrix
2690 {
2691  return ConstIterator( matrix_, 0UL, col_ );
2692 }
2694 //*************************************************************************************************
2695 
2696 
2697 //*************************************************************************************************
2705 template< typename MT > // Type of the sparse matrix
2707 {
2708  return Iterator( matrix_, size(), col_ );
2709 }
2711 //*************************************************************************************************
2712 
2713 
2714 //*************************************************************************************************
2722 template< typename MT > // Type of the sparse matrix
2725 {
2726  return ConstIterator( matrix_, size(), col_ );
2727 }
2729 //*************************************************************************************************
2730 
2731 
2732 //*************************************************************************************************
2740 template< typename MT > // Type of the sparse matrix
2743 {
2744  return ConstIterator( matrix_, size(), col_ );
2745 }
2747 //*************************************************************************************************
2748 
2749 
2750 
2751 
2752 //=================================================================================================
2753 //
2754 // ASSIGNMENT OPERATORS
2755 //
2756 //=================================================================================================
2757 
2758 //*************************************************************************************************
2772 template< typename MT > // Type of the sparse matrix
2773 inline Column<MT,false,false,false>&
2774  Column<MT,false,false,false>::operator=( const Column& rhs )
2775 {
2776  using blaze::assign;
2777 
2781 
2782  if( this == &rhs || ( &matrix_ == &rhs.matrix_ && col_ == rhs.col_ ) )
2783  return *this;
2784 
2785  if( size() != rhs.size() ) {
2786  BLAZE_THROW_INVALID_ARGUMENT( "Column sizes do not match" );
2787  }
2788 
2789  if( !tryAssign( matrix_, rhs, 0UL, col_ ) ) {
2790  BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted matrix" );
2791  }
2792 
2793  decltype(auto) left( derestrict( *this ) );
2794 
2795  if( rhs.canAlias( &matrix_ ) ) {
2796  const ResultType tmp( rhs );
2797  assign( left, tmp );
2798  }
2799  else {
2800  assign( left, rhs );
2801  }
2802 
2803  BLAZE_INTERNAL_ASSERT( isIntact( matrix_ ), "Invariant violation detected" );
2804 
2805  return *this;
2806 }
2808 //*************************************************************************************************
2809 
2810 
2811 //*************************************************************************************************
2825 template< typename MT > // Type of the sparse matrix
2826 template< typename VT > // Type of the right-hand side vector
2827 inline Column<MT,false,false,false>&
2828  Column<MT,false,false,false>::operator=( const Vector<VT,false>& rhs )
2829 {
2830  using blaze::assign;
2831 
2832  if( size() != (~rhs).size() ) {
2833  BLAZE_THROW_INVALID_ARGUMENT( "Vector sizes do not match" );
2834  }
2835 
2836  const CompositeType_<VT> tmp( ~rhs );
2837 
2838  if( !tryAssign( matrix_, tmp, 0UL, col_ ) ) {
2839  BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted matrix" );
2840  }
2841 
2842  decltype(auto) left( derestrict( *this ) );
2843 
2844  assign( left, tmp );
2845 
2846  BLAZE_INTERNAL_ASSERT( isIntact( matrix_ ), "Invariant violation detected" );
2847 
2848  return *this;
2849 }
2851 //*************************************************************************************************
2852 
2853 
2854 //*************************************************************************************************
2868 template< typename MT > // Type of the sparse matrix
2869 template< typename VT > // Type of the right-hand side vector
2870 inline Column<MT,false,false,false>&
2871  Column<MT,false,false,false>::operator+=( const Vector<VT,false>& rhs )
2872 {
2873  using blaze::assign;
2874 
2878  BLAZE_CONSTRAINT_MUST_BE_COLUMN_VECTOR_TYPE ( ResultType_<VT> );
2880 
2881  using AddType = AddTrait_< ResultType, ResultType_<VT> >;
2882 
2885 
2886  if( size() != (~rhs).size() ) {
2887  BLAZE_THROW_INVALID_ARGUMENT( "Vector sizes do not match" );
2888  }
2889 
2890  const AddType tmp( *this + (~rhs) );
2891 
2892  if( !tryAssign( matrix_, tmp, 0UL, col_ ) ) {
2893  BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted matrix" );
2894  }
2895 
2896  decltype(auto) left( derestrict( *this ) );
2897 
2898  assign( left, tmp );
2899 
2900  BLAZE_INTERNAL_ASSERT( isIntact( matrix_ ), "Invariant violation detected" );
2901 
2902  return *this;
2903 }
2905 //*************************************************************************************************
2906 
2907 
2908 //*************************************************************************************************
2922 template< typename MT > // Type of the sparse matrix
2923 template< typename VT > // Type of the right-hand side vector
2924 inline Column<MT,false,false,false>&
2925  Column<MT,false,false,false>::operator-=( const Vector<VT,false>& rhs )
2926 {
2927  using blaze::assign;
2928 
2932  BLAZE_CONSTRAINT_MUST_BE_COLUMN_VECTOR_TYPE ( ResultType_<VT> );
2934 
2935  using SubType = SubTrait_< ResultType, ResultType_<VT> >;
2936 
2939 
2940  if( size() != (~rhs).size() ) {
2941  BLAZE_THROW_INVALID_ARGUMENT( "Vector sizes do not match" );
2942  }
2943 
2944  const SubType tmp( *this - (~rhs) );
2945 
2946  if( !tryAssign( matrix_, tmp, 0UL, col_ ) ) {
2947  BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted matrix" );
2948  }
2949 
2950  decltype(auto) left( derestrict( *this ) );
2951 
2952  assign( left, tmp );
2953 
2954  BLAZE_INTERNAL_ASSERT( isIntact( matrix_ ), "Invariant violation detected" );
2955 
2956  return *this;
2957 }
2959 //*************************************************************************************************
2960 
2961 
2962 //*************************************************************************************************
2975 template< typename MT > // Type of the sparse matrix
2976 template< typename VT > // Type of the right-hand side vector
2977 inline Column<MT,false,false,false>&
2978  Column<MT,false,false,false>::operator*=( const Vector<VT,false>& rhs )
2979 {
2980  using blaze::assign;
2981 
2985  BLAZE_CONSTRAINT_MUST_BE_COLUMN_VECTOR_TYPE ( ResultType_<VT> );
2987 
2988  using MultType = MultTrait_< ResultType, ResultType_<VT> >;
2989 
2992 
2993  if( size() != (~rhs).size() ) {
2994  BLAZE_THROW_INVALID_ARGUMENT( "Vector sizes do not match" );
2995  }
2996 
2997  const MultType tmp( *this * (~rhs) );
2998 
2999  if( !tryAssign( matrix_, tmp, 0UL, col_ ) ) {
3000  BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted matrix" );
3001  }
3002 
3003  decltype(auto) left( derestrict( *this ) );
3004 
3005  assign( left, tmp );
3006 
3007  BLAZE_INTERNAL_ASSERT( isIntact( matrix_ ), "Invariant violation detected" );
3008 
3009  return *this;
3010 }
3012 //*************************************************************************************************
3013 
3014 
3015 //*************************************************************************************************
3027 template< typename MT > // Type of the sparse matrix
3028 template< typename VT > // Type of the right-hand side vector
3029 inline Column<MT,false,false,false>&
3030  Column<MT,false,false,false>::operator/=( const DenseVector<VT,false>& rhs )
3031 {
3032  using blaze::assign;
3033 
3037  BLAZE_CONSTRAINT_MUST_BE_DENSE_VECTOR_TYPE ( ResultType_<VT> );
3038  BLAZE_CONSTRAINT_MUST_BE_COLUMN_VECTOR_TYPE ( ResultType_<VT> );
3040 
3041  using DivType = DivTrait_< ResultType, ResultType_<VT> >;
3042 
3046 
3047  if( size() != (~rhs).size() ) {
3048  BLAZE_THROW_INVALID_ARGUMENT( "Vector sizes do not match" );
3049  }
3050 
3051  const DivType tmp( *this / (~rhs) );
3052 
3053  if( !tryAssign( matrix_, tmp, 0UL, col_ ) ) {
3054  BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted matrix" );
3055  }
3056 
3057  decltype(auto) left( derestrict( *this ) );
3058 
3059  assign( left, tmp );
3060 
3061  BLAZE_INTERNAL_ASSERT( isIntact( matrix_ ), "Invariant violation detected" );
3062 
3063  return *this;
3064 }
3066 //*************************************************************************************************
3067 
3068 
3069 //*************************************************************************************************
3082 template< typename MT > // Type of the sparse matrix
3083 template< typename VT > // Type of the right-hand side vector
3084 inline Column<MT,false,false,false>&
3085  Column<MT,false,false,false>::operator%=( const Vector<VT,false>& rhs )
3086 {
3087  using blaze::assign;
3088 
3089  BLAZE_CONSTRAINT_MUST_BE_COLUMN_VECTOR_TYPE ( ResultType_<VT> );
3091 
3092  using CrossType = CrossTrait_< ResultType, ResultType_<VT> >;
3093 
3097 
3098  if( size() != 3UL || (~rhs).size() != 3UL ) {
3099  BLAZE_THROW_INVALID_ARGUMENT( "Invalid vector size for cross product" );
3100  }
3101 
3102  const CrossType tmp( *this % (~rhs) );
3103 
3104  if( !tryAssign( matrix_, tmp, 0UL, col_ ) ) {
3105  BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted matrix" );
3106  }
3107 
3108  decltype(auto) left( derestrict( *this ) );
3109 
3110  assign( left, tmp );
3111 
3112  BLAZE_INTERNAL_ASSERT( isIntact( matrix_ ), "Invariant violation detected" );
3113 
3114  return *this;
3115 }
3117 //*************************************************************************************************
3118 
3119 
3120 //*************************************************************************************************
3135 template< typename MT > // Type of the sparse matrix
3136 template< typename Other > // Data type of the right-hand side scalar
3137 inline EnableIf_<IsNumeric<Other>, Column<MT,false,false,false> >&
3138  Column<MT,false,false,false>::operator*=( Other rhs )
3139 {
3141 
3142  for( Iterator element=begin(); element!=end(); ++element )
3143  element->value() *= rhs;
3144  return *this;
3145 }
3147 //*************************************************************************************************
3148 
3149 
3150 //*************************************************************************************************
3168 template< typename MT > // Type of the sparse matrix
3169 template< typename Other > // Data type of the right-hand side scalar
3170 inline EnableIf_<IsNumeric<Other>, Column<MT,false,false,false> >&
3172 {
3174 
3175  BLAZE_USER_ASSERT( rhs != Other(0), "Division by zero detected" );
3176 
3177  using DT = DivTrait_<ElementType,Other>;
3178  using Tmp = If_< IsNumeric<DT>, DT, Other >;
3179 
3180  // Depending on the two involved data types, an integer division is applied or a
3181  // floating point division is selected.
3182  if( IsNumeric<DT>::value && IsFloatingPoint<DT>::value ) {
3183  const Tmp tmp( Tmp(1)/static_cast<Tmp>( rhs ) );
3184  for( Iterator element=begin(); element!=end(); ++element )
3185  element->value() *= tmp;
3186  }
3187  else {
3188  for( Iterator element=begin(); element!=end(); ++element )
3189  element->value() /= rhs;
3190  }
3191 
3192  return *this;
3193 }
3195 //*************************************************************************************************
3196 
3197 
3198 
3199 
3200 //=================================================================================================
3201 //
3202 // UTILITY FUNCTIONS
3203 //
3204 //=================================================================================================
3205 
3206 //*************************************************************************************************
3212 template< typename MT > // Type of the sparse matrix
3213 inline typename Column<MT,false,false,false>::Operand
3214  Column<MT,false,false,false>::operand() const noexcept
3215 {
3216  return matrix_;
3217 }
3219 //*************************************************************************************************
3220 
3221 
3222 //*************************************************************************************************
3228 template< typename MT > // Type of the sparse matrix
3229 inline size_t Column<MT,false,false,false>::column() const noexcept
3230 {
3231  return col_;
3232 }
3234 //*************************************************************************************************
3235 
3236 
3237 //*************************************************************************************************
3243 template< typename MT > // Type of the sparse matrix
3244 inline size_t Column<MT,false,false,false>::size() const
3245 {
3246  return matrix_.rows();
3247 }
3249 //*************************************************************************************************
3250 
3251 
3252 //*************************************************************************************************
3258 template< typename MT > // Type of the sparse matrix
3259 inline size_t Column<MT,false,false,false>::capacity() const
3260 {
3261  return matrix_.rows();
3262 }
3264 //*************************************************************************************************
3265 
3266 
3267 //*************************************************************************************************
3276 template< typename MT > // Type of the sparse matrix
3277 inline size_t Column<MT,false,false,false>::nonZeros() const
3278 {
3279  size_t counter( 0UL );
3280  for( ConstIterator element=begin(); element!=end(); ++element ) {
3281  ++counter;
3282  }
3283  return counter;
3284 }
3286 //*************************************************************************************************
3287 
3288 
3289 //*************************************************************************************************
3295 template< typename MT > // Type of the sparse matrix
3297 {
3298  const size_t ibegin( ( IsLower<MT>::value )
3299  ?( ( IsUniLower<MT>::value || IsStrictlyLower<MT>::value )
3300  ?( col_+1UL )
3301  :( col_ ) )
3302  :( 0UL ) );
3303  const size_t iend ( ( IsUpper<MT>::value )
3304  ?( ( IsUniUpper<MT>::value || IsStrictlyUpper<MT>::value )
3305  ?( col_ )
3306  :( col_+1UL ) )
3307  :( size() ) );
3308 
3309  for( size_t i=ibegin; i<iend; ++i ) {
3310  matrix_.erase( i, col_ );
3311  }
3312 }
3314 //*************************************************************************************************
3315 
3316 
3317 //*************************************************************************************************
3327 template< typename MT > // Type of the sparse matrix
3328 void Column<MT,false,false,false>::reserve( size_t n )
3329 {
3330  UNUSED_PARAMETER( n );
3331 
3332  return;
3333 }
3335 //*************************************************************************************************
3336 
3337 
3338 
3339 
3340 //=================================================================================================
3341 //
3342 // INSERTION FUNCTIONS
3343 //
3344 //=================================================================================================
3345 
3346 //*************************************************************************************************
3358 template< typename MT > // Type of the sparse matrix
3360  Column<MT,false,false,false>::set( size_t index, const ElementType& value )
3361 {
3362  return Iterator( matrix_, index, col_, matrix_.set( index, col_, value ) );
3363 }
3365 //*************************************************************************************************
3366 
3367 
3368 //*************************************************************************************************
3381 template< typename MT > // Type of the sparse matrix
3383  Column<MT,false,false,false>::insert( size_t index, const ElementType& value )
3384 {
3385  return Iterator( matrix_, index, col_, matrix_.insert( index, col_, value ) );
3386 }
3388 //*************************************************************************************************
3389 
3390 
3391 //*************************************************************************************************
3416 template< typename MT > // Type of the sparse matrix
3417 inline void Column<MT,false,false,false>::append( size_t index, const ElementType& value, bool check )
3418 {
3419  if( !check || !isDefault( value ) )
3420  matrix_.insert( index, col_, value );
3421 }
3423 //*************************************************************************************************
3424 
3425 
3426 
3427 
3428 //=================================================================================================
3429 //
3430 // ERASE FUNCTIONS
3431 //
3432 //=================================================================================================
3433 
3434 //*************************************************************************************************
3443 template< typename MT > // Type of the sparse matrix
3444 inline void Column<MT,false,false,false>::erase( size_t index )
3445 {
3446  matrix_.erase( index, col_ );
3447 }
3449 //*************************************************************************************************
3450 
3451 
3452 //*************************************************************************************************
3461 template< typename MT > // Type of the sparse matrix
3463  Column<MT,false,false,false>::erase( Iterator pos )
3464 {
3465  const size_t row( pos.row_ );
3466 
3467  if( row == size() )
3468  return pos;
3469 
3470  matrix_.erase( row, pos.pos_ );
3471  return Iterator( matrix_, row+1UL, col_ );
3472 }
3474 //*************************************************************************************************
3475 
3476 
3477 //*************************************************************************************************
3487 template< typename MT > // Type of the sparse matrix
3489  Column<MT,false,false,false>::erase( Iterator first, Iterator last )
3490 {
3491  for( ; first!=last; ++first ) {
3492  matrix_.erase( first.row_, first.pos_ );
3493  }
3494  return last;
3495 }
3497 //*************************************************************************************************
3498 
3499 
3500 //*************************************************************************************************
3523 template< typename MT > // Type of the sparse matrix
3524 template< typename Pred // Type of the unary predicate
3525  , typename > // Type restriction on the unary predicate
3526 inline void Column<MT,false,false,false>::erase( Pred predicate )
3527 {
3528  for( Iterator element=begin(); element!=end(); ++element ) {
3529  if( predicate( element->value() ) )
3530  matrix_.erase( element.row_, element.pos_ );
3531  }
3532 }
3534 //*************************************************************************************************
3535 
3536 
3537 //*************************************************************************************************
3563 template< typename MT > // Type of the sparse matrix
3564 template< typename Pred > // Type of the unary predicate
3565 inline void Column<MT,false,false,false>::erase( Iterator first, Iterator last, Pred predicate )
3566 {
3567  for( ; first!=last; ++first ) {
3568  if( predicate( first->value() ) )
3569  matrix_.erase( first.row_, first.pos_ );
3570  }
3571 }
3573 //*************************************************************************************************
3574 
3575 
3576 
3577 
3578 //=================================================================================================
3579 //
3580 // LOOKUP FUNCTIONS
3581 //
3582 //=================================================================================================
3583 
3584 //*************************************************************************************************
3598 template< typename MT > // Type of the sparse matrix
3600  Column<MT,false,false,false>::find( size_t index )
3601 {
3602  const Iterator_<MT> pos( matrix_.find( index, col_ ) );
3603 
3604  if( pos != matrix_.end( index ) )
3605  return Iterator( matrix_, index, col_, pos );
3606  else
3607  return end();
3608 }
3610 //*************************************************************************************************
3611 
3612 
3613 //*************************************************************************************************
3627 template< typename MT > // Type of the sparse matrix
3629  Column<MT,false,false,false>::find( size_t index ) const
3630 {
3631  const ConstIterator_<MT> pos( matrix_.find( index, col_ ) );
3632 
3633  if( pos != matrix_.end( index ) )
3634  return ConstIterator( matrix_, index, col_, pos );
3635  else
3636  return end();
3637 }
3639 //*************************************************************************************************
3640 
3641 
3642 //*************************************************************************************************
3655 template< typename MT > // Type of the sparse matrix
3657  Column<MT,false,false,false>::lowerBound( size_t index )
3658 {
3659  for( size_t i=index; i<size(); ++i )
3660  {
3661  const Iterator_<MT> pos( matrix_.find( i, col_ ) );
3662 
3663  if( pos != matrix_.end( i ) )
3664  return Iterator( matrix_, i, col_, pos );
3665  }
3666 
3667  return end();
3668 }
3670 //*************************************************************************************************
3671 
3672 
3673 //*************************************************************************************************
3686 template< typename MT > // Type of the sparse matrix
3688  Column<MT,false,false,false>::lowerBound( size_t index ) const
3689 {
3690  for( size_t i=index; i<size(); ++i )
3691  {
3692  const ConstIterator_<MT> pos( matrix_.find( i, col_ ) );
3693 
3694  if( pos != matrix_.end( i ) )
3695  return ConstIterator( matrix_, i, col_, pos );
3696  }
3697 
3698  return end();
3699 }
3701 //*************************************************************************************************
3702 
3703 
3704 //*************************************************************************************************
3717 template< typename MT > // Type of the sparse matrix
3719  Column<MT,false,false,false>::upperBound( size_t index )
3720 {
3721  for( size_t i=index+1UL; i<size(); ++i )
3722  {
3723  const Iterator_<MT> pos( matrix_.find( i, col_ ) );
3724 
3725  if( pos != matrix_.end( i ) )
3726  return Iterator( matrix_, i, col_, pos );
3727  }
3728 
3729  return end();
3730 }
3732 //*************************************************************************************************
3733 
3734 
3735 //*************************************************************************************************
3748 template< typename MT > // Type of the sparse matrix
3750  Column<MT,false,false,false>::upperBound( size_t index ) const
3751 {
3752  for( size_t i=index+1UL; i<size(); ++i )
3753  {
3754  const ConstIterator_<MT> pos( matrix_.find( i, col_ ) );
3755 
3756  if( pos != matrix_.end( i ) )
3757  return ConstIterator( matrix_, i, col_, pos );
3758  }
3759 
3760  return end();
3761 }
3763 //*************************************************************************************************
3764 
3765 
3766 
3767 
3768 //=================================================================================================
3769 //
3770 // NUMERIC FUNCTIONS
3771 //
3772 //=================================================================================================
3773 
3774 //*************************************************************************************************
3787 template< typename MT > // Type of the sparse matrix
3788 template< typename Other > // Data type of the scalar value
3789 inline Column<MT,false,false,false>& Column<MT,false,false,false>::scale( const Other& scalar )
3790 {
3792 
3793  for( Iterator element=begin(); element!=end(); ++element )
3794  element->value() *= scalar;
3795  return *this;
3796 }
3798 //*************************************************************************************************
3799 
3800 
3801 
3802 
3803 //=================================================================================================
3804 //
3805 // EXPRESSION TEMPLATE EVALUATION FUNCTIONS
3806 //
3807 //=================================================================================================
3808 
3809 //*************************************************************************************************
3820 template< typename MT > // Type of the sparse matrix
3821 template< typename Other > // Data type of the foreign expression
3822 inline bool Column<MT,false,false,false>::canAlias( const Other* alias ) const
3823 {
3824  return matrix_.isAliased( alias );
3825 }
3827 //*************************************************************************************************
3828 
3829 
3830 //*************************************************************************************************
3837 template< typename MT > // Type of the sparse matrix
3838 template< typename Other > // Data type of the foreign expression
3839 inline bool Column<MT,false,false,false>::isAliased( const Other* alias ) const
3840 {
3841  return matrix_.isAliased( alias );
3842 }
3844 //*************************************************************************************************
3845 
3846 
3847 //*************************************************************************************************
3859 template< typename MT > // Type of the sparse matrix
3860 template< typename VT > // Type of the right-hand side dense vector
3861 inline void Column<MT,false,false,false>::assign( const DenseVector<VT,false>& rhs )
3862 {
3863  BLAZE_INTERNAL_ASSERT( size() == (~rhs).size(), "Invalid vector sizes" );
3864 
3865  for( size_t i=0UL; i<(~rhs).size(); ++i ) {
3866  matrix_(i,col_) = (~rhs)[i];
3867  }
3868 }
3870 //*************************************************************************************************
3871 
3872 
3873 //*************************************************************************************************
3885 template< typename MT > // Type of the sparse matrix
3886 template< typename VT > // Type of the right-hand side sparse vector
3887 inline void Column<MT,false,false,false>::assign( const SparseVector<VT,false>& rhs )
3888 {
3889  BLAZE_INTERNAL_ASSERT( size() == (~rhs).size(), "Invalid vector sizes" );
3890 
3891  size_t i( 0UL );
3892 
3893  for( ConstIterator_<VT> element=(~rhs).begin(); element!=(~rhs).end(); ++element ) {
3894  for( ; i<element->index(); ++i )
3895  matrix_.erase( i, col_ );
3896  matrix_(i++,col_) = element->value();
3897  }
3898  for( ; i<size(); ++i ) {
3899  matrix_.erase( i, col_ );
3900  }
3901 }
3903 //*************************************************************************************************
3904 
3905 
3906 //*************************************************************************************************
3918 template< typename MT > // Type of the sparse matrix
3919 template< typename VT > // Type of the right-hand side vector
3920 inline void Column<MT,false,false,false>::addAssign( const Vector<VT,false>& rhs )
3921 {
3922  using AddType = AddTrait_< ResultType, ResultType_<VT> >;
3923 
3926 
3927  BLAZE_INTERNAL_ASSERT( size() == (~rhs).size(), "Invalid vector sizes" );
3928 
3929  const AddType tmp( serial( *this + (~rhs) ) );
3930  assign( tmp );
3931 }
3933 //*************************************************************************************************
3934 
3935 
3936 //*************************************************************************************************
3948 template< typename MT > // Type of the sparse matrix
3949 template< typename VT > // Type of the right-hand side vector
3950 inline void Column<MT,false,false,false>::subAssign( const Vector<VT,false>& rhs )
3951 {
3952  using SubType = SubTrait_< ResultType, ResultType_<VT> >;
3953 
3956 
3957  BLAZE_INTERNAL_ASSERT( size() == (~rhs).size(), "Invalid vector sizes" );
3958 
3959  const SubType tmp( serial( *this - (~rhs) ) );
3960  assign( tmp );
3961 }
3963 //*************************************************************************************************
3964 
3965 
3966 
3967 
3968 
3969 
3970 
3971 
3972 //=================================================================================================
3973 //
3974 // CLASS TEMPLATE SPECIALIZATION FOR SYMMETRIC ROW-MAJOR SPARSE MATRICES
3975 //
3976 //=================================================================================================
3977 
3978 //*************************************************************************************************
3986 template< typename MT > // Type of the sparse matrix
3987 class Column<MT,false,false,true>
3988  : public View< SparseVector< Column<MT,false,false,true>, false > >
3989 {
3990  private:
3991  //**Type definitions****************************************************************************
3993  using Operand = If_< IsExpression<MT>, MT, MT& >;
3994  //**********************************************************************************************
3995 
3996  public:
3997  //**Type definitions****************************************************************************
3998  using This = Column<MT,false,false,true>;
3999  using BaseType = SparseVector<This,false>;
4000  using ResultType = ColumnTrait_<MT>;
4001  using TransposeType = TransposeType_<ResultType>;
4002  using ElementType = ElementType_<MT>;
4003  using ReturnType = ReturnType_<MT>;
4004  using CompositeType = const Column&;
4005 
4007  using ConstReference = ConstReference_<MT>;
4008 
4010  using Reference = If_< IsConst<MT>, ConstReference, Reference_<MT> >;
4011 
4013  using ConstIterator = ConstIterator_<MT>;
4014 
4016  using Iterator = If_< IsConst<MT>, ConstIterator, Iterator_<MT> >;
4017  //**********************************************************************************************
4018 
4019  //**Compilation flags***************************************************************************
4021  enum : bool { smpAssignable = false };
4022  //**********************************************************************************************
4023 
4024  //**Constructors********************************************************************************
4027  explicit inline Column( Operand matrix, size_t index );
4028  // No explicitly declared copy constructor.
4030  //**********************************************************************************************
4031 
4032  //**Destructor**********************************************************************************
4033  // No explicitly declared destructor.
4034  //**********************************************************************************************
4035 
4036  //**Data access functions***********************************************************************
4039  inline Reference operator[]( size_t index );
4040  inline ConstReference operator[]( size_t index ) const;
4041  inline Reference at( size_t index );
4042  inline ConstReference at( size_t index ) const;
4043  inline Iterator begin ();
4044  inline ConstIterator begin () const;
4045  inline ConstIterator cbegin() const;
4046  inline Iterator end ();
4047  inline ConstIterator end () const;
4048  inline ConstIterator cend () const;
4050  //**********************************************************************************************
4051 
4052  //**Assignment operators************************************************************************
4055  inline Column& operator=( const Column& rhs );
4056 
4057  template< typename VT > inline Column& operator= ( const DenseVector<VT,false>& rhs );
4058  template< typename VT > inline Column& operator= ( const SparseVector<VT,false>& rhs );
4059  template< typename VT > inline Column& operator+=( const DenseVector<VT,false>& rhs );
4060  template< typename VT > inline Column& operator+=( const SparseVector<VT,false>& rhs );
4061  template< typename VT > inline Column& operator-=( const DenseVector<VT,false>& rhs );
4062  template< typename VT > inline Column& operator-=( const SparseVector<VT,false>& rhs );
4063  template< typename VT > inline Column& operator*=( const Vector<VT,false>& rhs );
4064  template< typename VT > inline Column& operator/=( const DenseVector<VT,false>& rhs );
4065  template< typename VT > inline Column& operator%=( const Vector<VT,false>& rhs );
4066 
4067  template< typename Other >
4068  inline EnableIf_<IsNumeric<Other>, Column >& operator*=( Other rhs );
4069 
4070  template< typename Other >
4071  inline EnableIf_<IsNumeric<Other>, Column >& operator/=( Other rhs );
4073  //**********************************************************************************************
4074 
4075  //**Utility functions***************************************************************************
4078  inline Operand operand() const noexcept;
4079  inline size_t column() const noexcept;
4080  inline size_t size() const noexcept;
4081  inline size_t capacity() const noexcept;
4082  inline size_t nonZeros() const;
4083  inline void reset();
4084  inline void reserve( size_t n );
4086  //**********************************************************************************************
4087 
4088  //**Insertion functions*************************************************************************
4091  inline Iterator set ( size_t index, const ElementType& value );
4092  inline Iterator insert( size_t index, const ElementType& value );
4093  inline void append( size_t index, const ElementType& value, bool check=false );
4095  //**********************************************************************************************
4096 
4097  //**Erase functions*****************************************************************************
4100  inline void erase( size_t index );
4101  inline Iterator erase( Iterator pos );
4102  inline Iterator erase( Iterator first, Iterator last );
4103 
4104  template< typename Pred, typename = DisableIf_< IsIntegral<Pred> > >
4105  inline void erase( Pred predicate );
4106 
4107  template< typename Pred >
4108  inline void erase( Iterator first, Iterator last, Pred predicate );
4110  //**********************************************************************************************
4111 
4112  //**Lookup functions****************************************************************************
4115  inline Iterator find ( size_t index );
4116  inline ConstIterator find ( size_t index ) const;
4117  inline Iterator lowerBound( size_t index );
4118  inline ConstIterator lowerBound( size_t index ) const;
4119  inline Iterator upperBound( size_t index );
4120  inline ConstIterator upperBound( size_t index ) const;
4122  //**********************************************************************************************
4123 
4124  //**Numeric functions***************************************************************************
4127  template< typename Other > inline Column& scale( const Other& scalar );
4129  //**********************************************************************************************
4130 
4131  //**Expression template evaluation functions****************************************************
4134  template< typename Other > inline bool canAlias ( const Other* alias ) const noexcept;
4135  template< typename Other > inline bool isAliased( const Other* alias ) const noexcept;
4136 
4137  template< typename VT > inline void assign ( const DenseVector <VT,false>& rhs );
4138  template< typename VT > inline void assign ( const SparseVector<VT,false>& rhs );
4139  template< typename VT > inline void addAssign( const DenseVector <VT,false>& rhs );
4140  template< typename VT > inline void addAssign( const SparseVector<VT,false>& rhs );
4141  template< typename VT > inline void subAssign( const DenseVector <VT,false>& rhs );
4142  template< typename VT > inline void subAssign( const SparseVector<VT,false>& rhs );
4144  //**********************************************************************************************
4145 
4146  private:
4147  //**Utility functions***************************************************************************
4150  inline size_t extendCapacity() const noexcept;
4152  //**********************************************************************************************
4153 
4154  //**Member variables****************************************************************************
4157  Operand matrix_;
4158  const size_t col_;
4159 
4160  //**********************************************************************************************
4161 
4162  //**Compile time checks*************************************************************************
4170  //**********************************************************************************************
4171 };
4173 //*************************************************************************************************
4174 
4175 
4176 
4177 
4178 //=================================================================================================
4179 //
4180 // CONSTRUCTOR
4181 //
4182 //=================================================================================================
4183 
4184 //*************************************************************************************************
4192 template< typename MT > // Type of the sparse matrix
4193 inline Column<MT,false,false,true>::Column( Operand matrix, size_t index )
4194  : matrix_( matrix ) // The sparse matrix containing the column
4195  , col_ ( index ) // The index of the column in the matrix
4196 {
4197  if( matrix_.columns() <= index ) {
4198  BLAZE_THROW_INVALID_ARGUMENT( "Invalid column access index" );
4199  }
4200 }
4202 //*************************************************************************************************
4203 
4204 
4205 
4206 
4207 //=================================================================================================
4208 //
4209 // DATA ACCESS FUNCTIONS
4210 //
4211 //=================================================================================================
4212 
4213 //*************************************************************************************************
4223 template< typename MT > // Type of the sparse matrix
4225  Column<MT,false,false,true>::operator[]( size_t index )
4226 {
4227  BLAZE_USER_ASSERT( index < size(), "Invalid column access index" );
4228  return matrix_(col_,index);
4229 }
4231 //*************************************************************************************************
4232 
4233 
4234 //*************************************************************************************************
4244 template< typename MT > // Type of the sparse matrix
4246  Column<MT,false,false,true>::operator[]( size_t index ) const
4247 {
4248  BLAZE_USER_ASSERT( index < size(), "Invalid column access index" );
4249  return const_cast<const MT&>( matrix_ )(col_,index);
4250 }
4252 //*************************************************************************************************
4253 
4254 
4255 //*************************************************************************************************
4266 template< typename MT > // Type of the sparse matrix
4268  Column<MT,false,false,true>::at( size_t index )
4269 {
4270  if( index >= size() ) {
4271  BLAZE_THROW_OUT_OF_RANGE( "Invalid column access index" );
4272  }
4273  return (*this)[index];
4274 }
4276 //*************************************************************************************************
4277 
4278 
4279 //*************************************************************************************************
4290 template< typename MT > // Type of the sparse matrix
4292  Column<MT,false,false,true>::at( size_t index ) const
4293 {
4294  if( index >= size() ) {
4295  BLAZE_THROW_OUT_OF_RANGE( "Invalid column access index" );
4296  }
4297  return (*this)[index];
4298 }
4300 //*************************************************************************************************
4301 
4302 
4303 //*************************************************************************************************
4311 template< typename MT > // Type of the sparse matrix
4313 {
4314  return matrix_.begin( col_ );
4315 }
4317 //*************************************************************************************************
4318 
4319 
4320 //*************************************************************************************************
4328 template< typename MT > // Type of the sparse matrix
4331 {
4332  return matrix_.cbegin( col_ );
4333 }
4335 //*************************************************************************************************
4336 
4337 
4338 //*************************************************************************************************
4346 template< typename MT > // Type of the sparse matrix
4349 {
4350  return matrix_.cbegin( col_ );
4351 }
4353 //*************************************************************************************************
4354 
4355 
4356 //*************************************************************************************************
4364 template< typename MT > // Type of the sparse matrix
4366 {
4367  return matrix_.end( col_ );
4368 }
4370 //*************************************************************************************************
4371 
4372 
4373 //*************************************************************************************************
4381 template< typename MT > // Type of the sparse matrix
4384 {
4385  return matrix_.cend( col_ );
4386 }
4388 //*************************************************************************************************
4389 
4390 
4391 //*************************************************************************************************
4399 template< typename MT > // Type of the sparse matrix
4402 {
4403  return matrix_.cend( col_ );
4404 }
4406 //*************************************************************************************************
4407 
4408 
4409 
4410 
4411 //=================================================================================================
4412 //
4413 // ASSIGNMENT OPERATORS
4414 //
4415 //=================================================================================================
4416 
4417 //*************************************************************************************************
4431 template< typename MT > // Type of the sparse matrix
4432 inline Column<MT,false,false,true>& Column<MT,false,false,true>::operator=( const Column& rhs )
4433 {
4434  using blaze::assign;
4435 
4439 
4440  if( this == &rhs || ( &matrix_ == &rhs.matrix_ && col_ == rhs.col_ ) )
4441  return *this;
4442 
4443  if( size() != rhs.size() ) {
4444  BLAZE_THROW_INVALID_ARGUMENT( "Column sizes do not match" );
4445  }
4446 
4447  if( !tryAssign( matrix_, rhs, 0UL, col_ ) ) {
4448  BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted matrix" );
4449  }
4450 
4451  decltype(auto) left( derestrict( *this ) );
4452 
4453  if( rhs.canAlias( &matrix_ ) ) {
4454  const ResultType tmp( rhs );
4455  left.reset();
4456  left.reserve( tmp.nonZeros() );
4457  assign( left, tmp );
4458  }
4459  else {
4460  left.reset();
4461  left.reserve( rhs.nonZeros() );
4462  assign( left, rhs );
4463  }
4464 
4465  BLAZE_INTERNAL_ASSERT( isIntact( matrix_ ), "Invariant violation detected" );
4466 
4467  return *this;
4468 }
4470 //*************************************************************************************************
4471 
4472 
4473 //*************************************************************************************************
4487 template< typename MT > // Type of the sparse matrix
4488 template< typename VT > // Type of the right-hand side dense vector
4489 inline Column<MT,false,false,true>&
4490  Column<MT,false,false,true>::operator=( const DenseVector<VT,false>& rhs )
4491 {
4492  using blaze::assign;
4493 
4494  BLAZE_CONSTRAINT_MUST_BE_DENSE_VECTOR_TYPE ( ResultType_<VT> );
4495  BLAZE_CONSTRAINT_MUST_BE_COLUMN_VECTOR_TYPE ( ResultType_<VT> );
4497 
4498  if( size() != (~rhs).size() ) {
4499  BLAZE_THROW_INVALID_ARGUMENT( "Vector sizes do not match" );
4500  }
4501 
4502  using Right = If_< IsRestricted<MT>, CompositeType_<VT>, const VT& >;
4503  Right right( ~rhs );
4504 
4505  if( !tryAssign( matrix_, right, 0UL, col_ ) ) {
4506  BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted matrix" );
4507  }
4508 
4509  decltype(auto) left( derestrict( *this ) );
4510 
4511  if( IsReference<Right>::value && right.canAlias( &matrix_ ) ) {
4512  const ResultType_<VT> tmp( right );
4513  left.reset();
4514  assign( left, tmp );
4515  }
4516  else {
4517  left.reset();
4518  assign( left, right );
4519  }
4520 
4521  BLAZE_INTERNAL_ASSERT( isIntact( matrix_ ), "Invariant violation detected" );
4522 
4523  return *this;
4524 }
4526 //*************************************************************************************************
4527 
4528 
4529 //*************************************************************************************************
4543 template< typename MT > // Type of the sparse matrix
4544 template< typename VT > // Type of the right-hand side sparse vector
4545 inline Column<MT,false,false,true>&
4546  Column<MT,false,false,true>::operator=( const SparseVector<VT,false>& rhs )
4547 {
4548  using blaze::assign;
4549 
4550  BLAZE_CONSTRAINT_MUST_BE_SPARSE_VECTOR_TYPE ( ResultType_<VT> );
4551  BLAZE_CONSTRAINT_MUST_BE_COLUMN_VECTOR_TYPE ( ResultType_<VT> );
4553 
4554  if( size() != (~rhs).size() ) {
4555  BLAZE_THROW_INVALID_ARGUMENT( "Vector sizes do not match" );
4556  }
4557 
4558  using Right = If_< IsRestricted<MT>, CompositeType_<VT>, const VT& >;
4559  Right right( ~rhs );
4560 
4561  if( !tryAssign( matrix_, right, 0UL, col_ ) ) {
4562  BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted matrix" );
4563  }
4564 
4565  decltype(auto) left( derestrict( *this ) );
4566 
4567  if( IsReference<Right>::value && right.canAlias( &matrix_ ) ) {
4568  const ResultType_<VT> tmp( right);
4569  left.reset();
4570  left.reserve( tmp.nonZeros() );
4571  assign( left, tmp );
4572  }
4573  else {
4574  left.reset();
4575  left.reserve( right.nonZeros() );
4576  assign( left, right );
4577  }
4578 
4579  BLAZE_INTERNAL_ASSERT( isIntact( matrix_ ), "Invariant violation detected" );
4580 
4581  return *this;
4582 }
4584 //*************************************************************************************************
4585 
4586 
4587 //*************************************************************************************************
4601 template< typename MT > // Type of the sparse matrix
4602 template< typename VT > // Type of the right-hand side dense vector
4603 inline Column<MT,false,false,true>&
4604  Column<MT,false,false,true>::operator+=( const DenseVector<VT,false>& rhs )
4605 {
4606  using blaze::assign;
4607 
4611  BLAZE_CONSTRAINT_MUST_BE_DENSE_VECTOR_TYPE ( ResultType_<VT> );
4612  BLAZE_CONSTRAINT_MUST_BE_COLUMN_VECTOR_TYPE ( ResultType_<VT> );
4614 
4615  using AddType = AddTrait_< ResultType, ResultType_<VT> >;
4616 
4620 
4621  if( size() != (~rhs).size() ) {
4622  BLAZE_THROW_INVALID_ARGUMENT( "Vector sizes do not match" );
4623  }
4624 
4625  const AddType tmp( *this + (~rhs) );
4626 
4627  if( !tryAssign( matrix_, tmp, 0UL, col_ ) ) {
4628  BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted matrix" );
4629  }
4630 
4631  decltype(auto) left( derestrict( *this ) );
4632 
4633  left.reset();
4634  assign( left, tmp );
4635 
4636  BLAZE_INTERNAL_ASSERT( isIntact( matrix_ ), "Invariant violation detected" );
4637 
4638  return *this;
4639 }
4641 //*************************************************************************************************
4642 
4643 
4644 //*************************************************************************************************
4658 template< typename MT > // Type of the sparse matrix
4659 template< typename VT > // Type of the right-hand side sparse vector
4660 inline Column<MT,false,false,true>&
4661  Column<MT,false,false,true>::operator+=( const SparseVector<VT,false>& rhs )
4662 {
4663  using blaze::assign;
4664 
4668  BLAZE_CONSTRAINT_MUST_BE_SPARSE_VECTOR_TYPE ( ResultType_<VT> );
4669  BLAZE_CONSTRAINT_MUST_BE_COLUMN_VECTOR_TYPE ( ResultType_<VT> );
4671 
4672  using AddType = AddTrait_< ResultType, ResultType_<VT> >;
4673 
4677 
4678  if( size() != (~rhs).size() ) {
4679  BLAZE_THROW_INVALID_ARGUMENT( "Vector sizes do not match" );
4680  }
4681 
4682  const AddType tmp( *this + (~rhs) );
4683 
4684  if( !tryAssign( matrix_, tmp, 0UL, col_ ) ) {
4685  BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted matrix" );
4686  }
4687 
4688  decltype(auto) left( derestrict( *this ) );
4689 
4690  left.reset();
4691  left.reserve( tmp.nonZeros() );
4692  assign( left, tmp );
4693 
4694  BLAZE_INTERNAL_ASSERT( isIntact( matrix_ ), "Invariant violation detected" );
4695 
4696  return *this;
4697 }
4699 //*************************************************************************************************
4700 
4701 
4702 //*************************************************************************************************
4717 template< typename MT > // Type of the sparse matrix
4718 template< typename VT > // Type of the right-hand side dense vector
4719 inline Column<MT,false,false,true>&
4720  Column<MT,false,false,true>::operator-=( const DenseVector<VT,false>& rhs )
4721 {
4722  using blaze::assign;
4723 
4727  BLAZE_CONSTRAINT_MUST_BE_DENSE_VECTOR_TYPE ( ResultType_<VT> );
4728  BLAZE_CONSTRAINT_MUST_BE_COLUMN_VECTOR_TYPE ( ResultType_<VT> );
4730 
4731  using SubType = SubTrait_< ResultType, ResultType_<VT> >;
4732 
4736 
4737  if( size() != (~rhs).size() ) {
4738  BLAZE_THROW_INVALID_ARGUMENT( "Vector sizes do not match" );
4739  }
4740 
4741  const SubType tmp( *this - (~rhs) );
4742 
4743  if( !tryAssign( matrix_, tmp, 0UL, col_ ) ) {
4744  BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted matrix" );
4745  }
4746 
4747  decltype(auto) left( derestrict( *this ) );
4748 
4749  left.reset();
4750  assign( left, tmp );
4751 
4752  BLAZE_INTERNAL_ASSERT( isIntact( matrix_ ), "Invariant violation detected" );
4753 
4754  return *this;
4755 }
4757 //*************************************************************************************************
4758 
4759 
4760 //*************************************************************************************************
4775 template< typename MT > // Type of the sparse matrix
4776 template< typename VT > // Type of the right-hand side sparse vector
4777 inline Column<MT,false,false,true>&
4778  Column<MT,false,false,true>::operator-=( const SparseVector<VT,false>& rhs )
4779 {
4780  using blaze::assign;
4781 
4785  BLAZE_CONSTRAINT_MUST_BE_SPARSE_VECTOR_TYPE ( ResultType_<VT> );
4786  BLAZE_CONSTRAINT_MUST_BE_COLUMN_VECTOR_TYPE ( ResultType_<VT> );
4788 
4789  using SubType = SubTrait_< ResultType, ResultType_<VT> >;
4790 
4794 
4795  if( size() != (~rhs).size() ) {
4796  BLAZE_THROW_INVALID_ARGUMENT( "Vector sizes do not match" );
4797  }
4798 
4799  const SubType tmp( *this - (~rhs) );
4800 
4801  if( !tryAssign( matrix_, tmp, 0UL, col_ ) ) {
4802  BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted matrix" );
4803  }
4804 
4805  decltype(auto) left( derestrict( *this ) );
4806 
4807  left.reset();
4808  left.reserve( tmp.nonZeros() );
4809  assign( left, tmp );
4810 
4811  BLAZE_INTERNAL_ASSERT( isIntact( matrix_ ), "Invariant violation detected" );
4812 
4813  return *this;
4814 }
4816 //*************************************************************************************************
4817 
4818 
4819 //*************************************************************************************************
4832 template< typename MT > // Type of the sparse matrix
4833 template< typename VT > // Type of the right-hand side vector
4834 inline Column<MT,false,false,true>&
4835  Column<MT,false,false,true>::operator*=( const Vector<VT,false>& rhs )
4836 {
4837  using blaze::assign;
4838 
4842  BLAZE_CONSTRAINT_MUST_BE_COLUMN_VECTOR_TYPE ( ResultType_<VT> );
4844 
4845  using MultType = MultTrait_< ResultType, ResultType_<VT> >;
4846 
4849 
4850  if( size() != (~rhs).size() ) {
4851  BLAZE_THROW_INVALID_ARGUMENT( "Vector sizes do not match" );
4852  }
4853 
4854  const MultType tmp( *this * (~rhs) );
4855 
4856  if( !tryAssign( matrix_, tmp, 0UL, col_ ) ) {
4857  BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted matrix" );
4858  }
4859 
4860  decltype(auto) left( derestrict( *this ) );
4861 
4862  left.reset();
4863  assign( left, tmp );
4864 
4865  BLAZE_INTERNAL_ASSERT( isIntact( matrix_ ), "Invariant violation detected" );
4866 
4867  return *this;
4868 }
4870 //*************************************************************************************************
4871 
4872 
4873 //*************************************************************************************************
4885 template< typename MT > // Type of the sparse matrix
4886 template< typename VT > // Type of the right-hand side vector
4887 inline Column<MT,false,false,true>&
4888  Column<MT,false,false,true>::operator/=( const DenseVector<VT,false>& rhs )
4889 {
4890  using blaze::assign;
4891 
4895  BLAZE_CONSTRAINT_MUST_BE_DENSE_VECTOR_TYPE ( ResultType_<VT> );
4896  BLAZE_CONSTRAINT_MUST_BE_COLUMN_VECTOR_TYPE ( ResultType_<VT> );
4898 
4899  using DivType = DivTrait_< ResultType, ResultType_<VT> >;
4900 
4904 
4905  if( size() != (~rhs).size() ) {
4906  BLAZE_THROW_INVALID_ARGUMENT( "Vector sizes do not match" );
4907  }
4908 
4909  const DivType tmp( *this / (~rhs) );
4910 
4911  if( !tryAssign( matrix_, tmp, 0UL, col_ ) ) {
4912  BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted matrix" );
4913  }
4914 
4915  decltype(auto) left( derestrict( *this ) );
4916 
4917  left.reset();
4918  assign( left, tmp );
4919 
4920  BLAZE_INTERNAL_ASSERT( isIntact( matrix_ ), "Invariant violation detected" );
4921 
4922  return *this;
4923 }
4925 //*************************************************************************************************
4926 
4927 
4928 //*************************************************************************************************
4941 template< typename MT > // Type of the sparse matrix
4942 template< typename VT > // Type of the right-hand side vector
4943 inline Column<MT,false,false,true>&
4944  Column<MT,false,false,true>::operator%=( const Vector<VT,false>& rhs )
4945 {
4946  using blaze::assign;
4947 
4948  BLAZE_CONSTRAINT_MUST_BE_COLUMN_VECTOR_TYPE ( ResultType_<VT> );
4950 
4951  using CrossType = CrossTrait_< ResultType, ResultType_<VT> >;
4952 
4956 
4957  if( size() != 3UL || (~rhs).size() != 3UL ) {
4958  BLAZE_THROW_INVALID_ARGUMENT( "Invalid vector size for cross product" );
4959  }
4960 
4961  const CrossType tmp( *this % (~rhs) );
4962 
4963  if( !tryAssign( matrix_, tmp, 0UL, col_ ) ) {
4964  BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted matrix" );
4965  }
4966 
4967  decltype(auto) left( derestrict( *this ) );
4968 
4969  left.reset();
4970  assign( left, tmp );
4971 
4972  BLAZE_INTERNAL_ASSERT( isIntact( matrix_ ), "Invariant violation detected" );
4973 
4974  return *this;
4975 }
4977 //*************************************************************************************************
4978 
4979 
4980 //*************************************************************************************************
4995 template< typename MT > // Type of the sparse matrix
4996 template< typename Other > // Data type of the right-hand side scalar
4997 inline EnableIf_<IsNumeric<Other>, Column<MT,false,false,true> >&
4998  Column<MT,false,false,true>::operator*=( Other rhs )
4999 {
5001 
5002  for( Iterator element=begin(); element!=end(); ++element )
5003  element->value() *= rhs;
5004  return *this;
5005 }
5007 //*************************************************************************************************
5008 
5009 
5010 //*************************************************************************************************
5028 template< typename MT > // Type of the sparse matrix
5029 template< typename Other > // Data type of the right-hand side scalar
5030 inline EnableIf_<IsNumeric<Other>, Column<MT,false,false,true> >&
5032 {
5034 
5035  BLAZE_USER_ASSERT( rhs != Other(0), "Division by zero detected" );
5036 
5037  using DT = DivTrait_<ElementType,Other>;
5038  using Tmp = If_< IsNumeric<DT>, DT, Other >;
5039 
5040  // Depending on the two involved data types, an integer division is applied or a
5041  // floating point division is selected.
5042  if( IsNumeric<DT>::value && IsFloatingPoint<DT>::value ) {
5043  const Tmp tmp( Tmp(1)/static_cast<Tmp>( rhs ) );
5044  for( Iterator element=begin(); element!=end(); ++element )
5045  element->value() *= tmp;
5046  }
5047  else {
5048  for( Iterator element=begin(); element!=end(); ++element )
5049  element->value() /= rhs;
5050  }
5051 
5052  return *this;
5053 }
5055 //*************************************************************************************************
5056 
5057 
5058 
5059 
5060 //=================================================================================================
5061 //
5062 // UTILITY FUNCTIONS
5063 //
5064 //=================================================================================================
5065 
5066 //*************************************************************************************************
5072 template< typename MT > // Type of the sparse matrix
5073 inline typename Column<MT,false,false,true>::Operand
5074  Column<MT,false,false,true>::operand() const noexcept
5075 {
5076  return matrix_;
5077 }
5079 //*************************************************************************************************
5080 
5081 
5082 //*************************************************************************************************
5088 template< typename MT > // Type of the sparse matrix
5089 inline size_t Column<MT,false,false,true>::column() const noexcept
5090 {
5091  return col_;
5092 }
5094 //*************************************************************************************************
5095 
5096 
5097 //*************************************************************************************************
5103 template< typename MT > // Type of the sparse matrix
5104 inline size_t Column<MT,false,false,true>::size() const noexcept
5105 {
5106  return matrix_.rows();
5107 }
5109 //*************************************************************************************************
5110 
5111 
5112 //*************************************************************************************************
5118 template< typename MT > // Type of the sparse matrix
5119 inline size_t Column<MT,false,false,true>::capacity() const noexcept
5120 {
5121  return matrix_.capacity( col_ );
5122 }
5124 //*************************************************************************************************
5125 
5126 
5127 //*************************************************************************************************
5136 template< typename MT > // Type of the sparse matrix
5137 inline size_t Column<MT,false,false,true>::nonZeros() const
5138 {
5139  return matrix_.nonZeros( col_ );
5140 }
5142 //*************************************************************************************************
5143 
5144 
5145 //*************************************************************************************************
5151 template< typename MT > // Type of the sparse matrix
5153 {
5154  matrix_.reset( col_ );
5155 }
5157 //*************************************************************************************************
5158 
5159 
5160 //*************************************************************************************************
5170 template< typename MT > // Type of the sparse matrix
5171 void Column<MT,false,false,true>::reserve( size_t n )
5172 {
5173  matrix_.reserve( col_, n );
5174 }
5176 //*************************************************************************************************
5177 
5178 
5179 //*************************************************************************************************
5188 template< typename MT > // Type of the sparse matrix
5189 inline size_t Column<MT,false,false,true>::extendCapacity() const noexcept
5190 {
5191  using blaze::max;
5192  using blaze::min;
5193 
5194  size_t nonzeros( 2UL*capacity()+1UL );
5195  nonzeros = max( nonzeros, 7UL );
5196  nonzeros = min( nonzeros, size() );
5197 
5198  BLAZE_INTERNAL_ASSERT( nonzeros > capacity(), "Invalid capacity value" );
5199 
5200  return nonzeros;
5201 }
5203 //*************************************************************************************************
5204 
5205 
5206 
5207 
5208 //=================================================================================================
5209 //
5210 // INSERTION FUNCTIONS
5211 //
5212 //=================================================================================================
5213 
5214 //*************************************************************************************************
5226 template< typename MT > // Type of the sparse matrix
5228  Column<MT,false,false,true>::set( size_t index, const ElementType& value )
5229 {
5230  return matrix_.set( col_, index, value );
5231 }
5233 //*************************************************************************************************
5234 
5235 
5236 //*************************************************************************************************
5249 template< typename MT > // Type of the sparse matrix
5251  Column<MT,false,false,true>::insert( size_t index, const ElementType& value )
5252 {
5253  return matrix_.insert( col_, index, value );
5254 }
5256 //*************************************************************************************************
5257 
5258 
5259 //*************************************************************************************************
5284 template< typename MT > // Type of the sparse matrix
5285 inline void Column<MT,false,false,true>::append( size_t index, const ElementType& value, bool check )
5286 {
5287  matrix_.append( col_, index, value, check );
5288 }
5290 //*************************************************************************************************
5291 
5292 
5293 
5294 
5295 //=================================================================================================
5296 //
5297 // ERASE FUNCTIONS
5298 //
5299 //=================================================================================================
5300 
5301 //*************************************************************************************************
5310 template< typename MT > // Type of the sparse matrix
5311 inline void Column<MT,false,false,true>::erase( size_t index )
5312 {
5313  matrix_.erase( col_, index );
5314 }
5316 //*************************************************************************************************
5317 
5318 
5319 //*************************************************************************************************
5328 template< typename MT > // Type of the sparse matrix
5330  Column<MT,false,false,true>::erase( Iterator pos )
5331 {
5332  return matrix_.erase( col_, pos );
5333 }
5335 //*************************************************************************************************
5336 
5337 
5338 //*************************************************************************************************
5348 template< typename MT > // Type of the sparse matrix
5350  Column<MT,false,false,true>::erase( Iterator first, Iterator last )
5351 {
5352  return matrix_.erase( col_, first, last );
5353 }
5355 //*************************************************************************************************
5356 
5357 
5358 //*************************************************************************************************
5381 template< typename MT > // Type of the sparse matrix
5382 template< typename Pred // Type of the unary predicate
5383  , typename > // Type restriction on the unary predicate
5384 inline void Column<MT,false,false,true>::erase( Pred predicate )
5385 {
5386  matrix_.erase( col_, begin(), end(), predicate );
5387 }
5389 //*************************************************************************************************
5390 
5391 
5392 //*************************************************************************************************
5417 template< typename MT > // Type of the sparse matrix
5418 template< typename Pred > // Type of the unary predicate
5419 inline void Column<MT,false,false,true>::erase( Iterator first, Iterator last, Pred predicate )
5420 {
5421  matrix_.erase( col_, first, last, predicate );
5422 }
5424 //*************************************************************************************************
5425 
5426 
5427 
5428 
5429 //=================================================================================================
5430 //
5431 // LOOKUP FUNCTIONS
5432 //
5433 //=================================================================================================
5434 
5435 //*************************************************************************************************
5449 template< typename MT > // Type of the sparse matrix
5451  Column<MT,false,false,true>::find( size_t index )
5452 {
5453  return matrix_.find( col_, index );
5454 }
5456 //*************************************************************************************************
5457 
5458 
5459 //*************************************************************************************************
5473 template< typename MT > // Type of the sparse matrix
5475  Column<MT,false,false,true>::find( size_t index ) const
5476 {
5477  return matrix_.find( col_, index );
5478 }
5480 //*************************************************************************************************
5481 
5482 
5483 //*************************************************************************************************
5496 template< typename MT > // Type of the sparse matrix
5498  Column<MT,false,false,true>::lowerBound( size_t index )
5499 {
5500  return matrix_.lowerBound( col_, index );
5501 }
5503 //*************************************************************************************************
5504 
5505 
5506 //*************************************************************************************************
5519 template< typename MT > // Type of the sparse matrix
5521  Column<MT,false,false,true>::lowerBound( size_t index ) const
5522 {
5523  return matrix_.lowerBound( col_, index );
5524 }
5526 //*************************************************************************************************
5527 
5528 
5529 //*************************************************************************************************
5542 template< typename MT > // Type of the sparse matrix
5544  Column<MT,false,false,true>::upperBound( size_t index )
5545 {
5546  return matrix_.upperBound( col_, index );
5547 }
5549 //*************************************************************************************************
5550 
5551 
5552 //*************************************************************************************************
5565 template< typename MT > // Type of the sparse matrix
5567  Column<MT,false,false,true>::upperBound( size_t index ) const
5568 {
5569  return matrix_.upperBound( col_, index );
5570 }
5572 //*************************************************************************************************
5573 
5574 
5575 
5576 
5577 //=================================================================================================
5578 //
5579 // NUMERIC FUNCTIONS
5580 //
5581 //=================================================================================================
5582 
5583 //*************************************************************************************************
5596 template< typename MT > // Type of the sparse matrix
5597 template< typename Other > // Data type of the scalar value
5598 inline Column<MT,false,false,true>& Column<MT,false,false,true>::scale( const Other& scalar )
5599 {
5601 
5602  for( Iterator element=begin(); element!=end(); ++element )
5603  element->value() *= scalar;
5604  return *this;
5605 }
5607 //*************************************************************************************************
5608 
5609 
5610 
5611 
5612 //=================================================================================================
5613 //
5614 // EXPRESSION TEMPLATE EVALUATION FUNCTIONS
5615 //
5616 //=================================================================================================
5617 
5618 //*************************************************************************************************
5629 template< typename MT > // Type of the sparse matrix
5630 template< typename Other > // Data type of the foreign expression
5631 inline bool Column<MT,false,false,true>::canAlias( const Other* alias ) const noexcept
5632 {
5633  return matrix_.isAliased( alias );
5634 }
5636 //*************************************************************************************************
5637 
5638 
5639 //*************************************************************************************************
5650 template< typename MT > // Type of the sparse matrix
5651 template< typename Other > // Data type of the foreign expression
5652 inline bool Column<MT,false,false,true>::isAliased( const Other* alias ) const noexcept
5653 {
5654  return matrix_.isAliased( alias );
5655 }
5657 //*************************************************************************************************
5658 
5659 
5660 //*************************************************************************************************
5672 template< typename MT > // Type of the sparse matrix
5673 template< typename VT > // Type of the right-hand side dense vector
5674 inline void Column<MT,false,false,true>::assign( const DenseVector<VT,false>& rhs )
5675 {
5676  BLAZE_INTERNAL_ASSERT( size() == (~rhs).size(), "Invalid vector sizes" );
5677  BLAZE_INTERNAL_ASSERT( nonZeros() == 0UL, "Invalid non-zero elements detected" );
5678 
5679  for( size_t i=0UL; i<size(); ++i )
5680  {
5681  if( matrix_.nonZeros( col_ ) == matrix_.capacity( col_ ) )
5682  matrix_.reserve( col_, extendCapacity() );
5683 
5684  matrix_.append( col_, i, (~rhs)[i], true );
5685  }
5686 }
5688 //*************************************************************************************************
5689 
5690 
5691 //*************************************************************************************************
5703 template< typename MT > // Type of the sparse matrix
5704 template< typename VT > // Type of the right-hand side sparse vector
5705 inline void Column<MT,false,false,true>::assign( const SparseVector<VT,false>& rhs )
5706 {
5707  BLAZE_INTERNAL_ASSERT( size() == (~rhs).size(), "Invalid vector sizes" );
5708  BLAZE_INTERNAL_ASSERT( nonZeros() == 0UL, "Invalid non-zero elements detected" );
5709 
5710  for( ConstIterator_<VT> element=(~rhs).begin(); element!=(~rhs).end(); ++element ) {
5711  matrix_.append( col_, element->index(), element->value(), true );
5712  }
5713 }
5715 //*************************************************************************************************
5716 
5717 
5718 //*************************************************************************************************
5730 template< typename MT > // Type of the sparse matrix
5731 template< typename VT > // Type of the right-hand side dense vector
5732 inline void Column<MT,false,false,true>::addAssign( const DenseVector<VT,false>& rhs )
5733 {
5734  using AddType = AddTrait_< ResultType, ResultType_<VT> >;
5735 
5739 
5740  BLAZE_INTERNAL_ASSERT( size() == (~rhs).size(), "Invalid vector sizes" );
5741 
5742  const AddType tmp( serial( *this + (~rhs) ) );
5743  matrix_.reset( col_ );
5744  assign( tmp );
5745 }
5747 //*************************************************************************************************
5748 
5749 
5750 //*************************************************************************************************
5762 template< typename MT > // Type of the sparse matrix
5763 template< typename VT > // Type of the right-hand side sparse vector
5764 inline void Column<MT,false,false,true>::addAssign( const SparseVector<VT,false>& rhs )
5765 {
5766  using AddType = AddTrait_< ResultType, ResultType_<VT> >;
5767 
5771 
5772  BLAZE_INTERNAL_ASSERT( size() == (~rhs).size(), "Invalid vector sizes" );
5773 
5774  const AddType tmp( serial( *this + (~rhs) ) );
5775  matrix_.reset( col_ );
5776  matrix_.reserve( col_, tmp.nonZeros() );
5777  assign( tmp );
5778 }
5780 //*************************************************************************************************
5781 
5782 
5783 //*************************************************************************************************
5795 template< typename MT > // Type of the sparse matrix
5796 template< typename VT > // Type of the right-hand side dense vector
5797 inline void Column<MT,false,false,true>::subAssign( const DenseVector<VT,false>& rhs )
5798 {
5799  using SubType = SubTrait_< ResultType, ResultType_<VT> >;
5800 
5804 
5805  BLAZE_INTERNAL_ASSERT( size() == (~rhs).size(), "Invalid vector sizes" );
5806 
5807  const SubType tmp( serial( *this - (~rhs) ) );
5808  matrix_.reset( col_ );
5809  assign( tmp );
5810 }
5812 //*************************************************************************************************
5813 
5814 
5815 //*************************************************************************************************
5827 template< typename MT > // Type of the sparse matrix
5828 template< typename VT > // Type of the right-hand side sparse vector
5829 inline void Column<MT,false,false,true>::subAssign( const SparseVector<VT,false>& rhs )
5830 {
5831  using SubType = SubTrait_< ResultType, ResultType_<VT> >;
5832 
5836 
5837  BLAZE_INTERNAL_ASSERT( size() == (~rhs).size(), "Invalid vector sizes" );
5838 
5839  const SubType tmp( serial( *this - (~rhs) ) );
5840  matrix_.reset( col_ );
5841  matrix_.reserve( col_, tmp.nonZeros() );
5842  assign( tmp );
5843 }
5845 //*************************************************************************************************
5846 
5847 } // namespace blaze
5848 
5849 #endif
#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
Constraint on the data type.
Header file for auxiliary alias declarations.
Headerfile for the generic min algorithm.
#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 UNUSED_PARAMETER function template.
Header file for the IsUniUpper type trait.
Header file for the subtraction trait.
BLAZE_ALWAYS_INLINE size_t capacity(const Matrix< MT, SO > &matrix) noexcept
Returns the maximum capacity of the matrix.
Definition: Matrix.h:356
Header file for basic type definitions.
Header file for the SparseVector base class.
Header file for the View base class.
#define BLAZE_CONSTRAINT_MUST_BE_COLUMN_VECTOR_TYPE(T)
Constraint on the data type.In case the given data type T is not a column dense or sparse vector type...
Definition: ColumnVector.h:61
Header file for the serial shim.
BLAZE_ALWAYS_INLINE size_t size(const Vector< VT, TF > &vector) noexcept
Returns the current size/dimension of the vector.
Definition: Vector.h:265
#define BLAZE_CONSTRAINT_MUST_NOT_BE_COMPUTATION_TYPE(T)
Constraint on the data type.In case the given data type T is a computational expression (i...
Definition: Computation.h:81
BLAZE_ALWAYS_INLINE T1 & operator/=(SIMDPack< T1 > &lhs, const SIMDPack< T2 > &rhs)
Division assignment operator for the division of two SIMD packs.
Definition: BasicTypes.h:1411
This ResultType
Result type for expression template evaluations.
Definition: CompressedMatrix.h:3078
BLAZE_ALWAYS_INLINE MT::Iterator begin(Matrix< MT, SO > &matrix, size_t i)
Returns an iterator to the first element of row/column i.
Definition: Matrix.h:198
CompressedMatrix< Type, true > This
Type of this CompressedMatrix instance.
Definition: CompressedMatrix.h:3076
Header file for the implementation of the Column base template.
void reset(const DiagonalProxy< MT > &proxy)
Resetting the represented element to the default initial values.
Definition: DiagonalProxy.h:560
typename DisableIf< Condition, T >::Type DisableIf_
Auxiliary type for the DisableIf class template.The DisableIf_ alias declaration provides a convenien...
Definition: DisableIf.h:224
Header file for the IsIntegral type trait.
CompressedMatrix< Type, false > TransposeType
Transpose type for expression template evaluations.
Definition: CompressedMatrix.h:3080
const ElementType_< MT > min(const DenseMatrix< MT, SO > &dm)
Returns the smallest element of the dense matrix.
Definition: DenseMatrix.h:1762
#define BLAZE_CONSTRAINT_MUST_NOT_BE_UNITRIANGULAR_MATRIX_TYPE(T)
Constraint on the data type.In case the given data type T is a lower or upper unitriangular matrix ty...
Definition: UniTriangular.h:81
const Type & ConstReference
Reference to a constant matrix value.
Definition: CompressedMatrix.h:3085
BLAZE_ALWAYS_INLINE size_t nonZeros(const Matrix< MT, SO > &matrix)
Returns the total number of non-zero elements in the matrix.
Definition: Matrix.h:394
Column< MT > column(Matrix< MT, SO > &matrix, size_t index)
Creating a view on a specific column of the given matrix.
Definition: Column.h:124
#define BLAZE_CONSTRAINT_MUST_BE_SYMMETRIC_MATRIX_TYPE(T)
Constraint on the data type.In case the given data type T is not a symmetric matrix type...
Definition: Symmetric.h:60
const DenseIterator< Type, AF > operator-(const DenseIterator< Type, AF > &it, ptrdiff_t inc) noexcept
Subtraction between a DenseIterator and an integral value.
Definition: DenseIterator.h:731
Element * Iterator
Iterator over non-constant elements.
Definition: CompressedMatrix.h:3086
Constraints on the storage order of matrix types.
#define BLAZE_CONSTRAINT_MUST_NOT_BE_TRANSEXPR_TYPE(T)
Constraint on the data type.In case the given data type T is a transposition expression (i...
Definition: TransExpr.h:81
BLAZE_ALWAYS_INLINE T1 & operator*=(SIMDPack< T1 > &lhs, const SIMDPack< T2 > &rhs)
Multiplication assignment operator for the multiplication of two SIMD packs.
Definition: BasicTypes.h:1393
Header file for the IsUniLower type trait.
const ElementType_< MT > max(const DenseMatrix< MT, SO > &dm)
Returns the largest element of the dense matrix.
Definition: DenseMatrix.h:1809
BLAZE_ALWAYS_INLINE MT::ConstIterator cend(const Matrix< MT, SO > &matrix, size_t i)
Returns an iterator just past the last element of row/column i.
Definition: Matrix.h:308
BLAZE_ALWAYS_INLINE MT::ConstIterator cbegin(const Matrix< MT, SO > &matrix, size_t i)
Returns an iterator to the first element of row/column i.
Definition: Matrix.h:242
Constraint on the data type.
Constraint on the transpose flag of vector types.
Row< MT > row(Matrix< MT, SO > &matrix, size_t index)
Creating a view on a specific row of the given matrix.
Definition: Row.h:124
Constraint on the data type.
Headerfile for the generic max algorithm.
Header file for the DisableIf class template.
Header file for the multiplication trait.
Header file for the IsStrictlyUpper type trait.
MatrixAccessProxy< This > Reference
Reference to a non-constant matrix value.
Definition: CompressedMatrix.h:3084
Namespace of the Blaze C++ math library.
Definition: Blaze.h:57
Header file for the If class template.
Header file for the IsFloatingPoint type trait.
#define BLAZE_CONSTRAINT_MUST_BE_COLUMN_MAJOR_MATRIX_TYPE(T)
Constraint on the data type.In case the given data type T is not a column-major dense or sparse matri...
Definition: ColumnMajorMatrix.h:61
SparseMatrix< This, true > BaseType
Base type of this CompressedMatrix instance.
Definition: CompressedMatrix.h:3077
#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
Type ElementType
Type of the compressed matrix elements.
Definition: CompressedMatrix.h:3081
#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
const Element * ConstIterator
Iterator over constant elements.
Definition: CompressedMatrix.h:3087
constexpr bool operator==(const NegativeAccuracy< A > &lhs, const T &rhs)
Equality comparison between a NegativeAccuracy object and a floating point value. ...
Definition: Accuracy.h:250
Header file for the IsLower type trait.
#define BLAZE_CONSTRAINT_MUST_BE_SPARSE_VECTOR_TYPE(T)
Constraint on the data type.In case the given data type T is not a sparse, N-dimensional vector type...
Definition: SparseVector.h:61
Header file for the SparseElement base class.
Constraint on the data type.
Constraint on the data type.
Header file for the exception macros of the math module.
BLAZE_ALWAYS_INLINE MT::Iterator end(Matrix< MT, SO > &matrix, size_t i)
Returns an iterator just past the last element of row/column i.
Definition: Matrix.h:264
decltype(auto) operator*(const DenseMatrix< MT1, false > &lhs, const DenseMatrix< MT2, false > &rhs)
Multiplication operator for the multiplication of two row-major dense matrices ( ).
Definition: DMatDMatMultExpr.h:8893
constexpr bool operator!=(const NegativeAccuracy< A > &lhs, const T &rhs)
Inequality comparison between a NegativeAccuracy object and a floating point value.
Definition: Accuracy.h:290
Constraint on the data type.
Constraint on the data type.
Header file for the EnableIf class template.
Header file for the IsStrictlyLower type trait.
Constraint on the data type.
Header file for the IsNumeric type trait.
BLAZE_ALWAYS_INLINE const EnableIf_< And< IsIntegral< T >, HasSize< T, 1UL > >, If_< IsSigned< T >, SIMDint8, SIMDuint8 > > set(T value) noexcept
Sets all values in the vector to the given 1-byte integral value.
Definition: Set.h:76
#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
#define BLAZE_CONSTRAINT_MUST_BE_ROW_MAJOR_MATRIX_TYPE(T)
Constraint on the data type.In case the given data type T is not a row-major dense or sparse matrix t...
Definition: RowMajorMatrix.h:61
Header file for the IsConst type trait.
BLAZE_ALWAYS_INLINE T1 & operator+=(SIMDPack< T1 > &lhs, const SIMDPack< T2 > &rhs)
Addition assignment operator for the addition of two SIMD packs.
Definition: BasicTypes.h:1357
Header file for run time assertion macros.
Header file for the addition trait.
Header file for the cross product trait.
Header file for the division trait.
Header file for the reset shim.
#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 column trait.
Header file for the isDefault shim.
Constraint on the data type.
Constraint on the data type.
Constraints on the storage order of matrix types.
decltype(auto) serial(const DenseMatrix< MT, SO > &dm)
Forces the serial evaluation of the given dense matrix expression dm.
Definition: DMatSerialExpr.h:819
#define BLAZE_CONSTRAINT_MUST_NOT_REQUIRE_EVALUATION(T)
Constraint on the data type.In case the given data type T requires an intermediate evaluation within ...
Definition: RequiresEvaluation.h:81
Header file for the IsReference type trait.
typename EnableIf< Condition, T >::Type EnableIf_
Auxiliary alias declaration for the EnableIf class template.The EnableIf_ alias declaration provides ...
Definition: EnableIf.h:224
const Type & ReturnType
Return type for expression template evaluations.
Definition: CompressedMatrix.h:3082
#define BLAZE_CONSTRAINT_MUST_BE_DENSE_VECTOR_TYPE(T)
Constraint on the data type.In case the given data type T is not a dense, N-dimensional vector type...
Definition: DenseVector.h:61
const This & CompositeType
Data type for composite expression templates.
Definition: CompressedMatrix.h:3083
bool isIntact(const DiagonalMatrix< MT, SO, DF > &m)
Returns whether the invariants of the given diagonal matrix are intact.
Definition: DiagonalMatrix.h:252
bool isDefault(const DiagonalProxy< MT > &proxy)
Returns whether the represented element is in default state.
Definition: DiagonalProxy.h:600
BLAZE_ALWAYS_INLINE T1 & operator-=(SIMDPack< T1 > &lhs, const SIMDPack< T2 > &rhs)
Subtraction assignment operator for the subtraction of two SIMD packs.
Definition: BasicTypes.h:1375
Header file for the IsUpper type trait.
void UNUSED_PARAMETER(const Args &...)
Suppression of unused parameter warnings.
Definition: Unused.h:81
Header file for the IsRestricted type trait.
#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
#define BLAZE_CONSTRAINT_MUST_BE_SPARSE_MATRIX_TYPE(T)
Constraint on the data type.In case the given data type T is not a sparse, N-dimensional matrix type...
Definition: SparseMatrix.h:61
Header file for the IsExpression type trait class.