All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
SparseColumn.h
Go to the documentation of this file.
1 //=================================================================================================
20 //=================================================================================================
21 
22 #ifndef _BLAZE_MATH_VIEWS_SPARSECOLUMN_H_
23 #define _BLAZE_MATH_VIEWS_SPARSECOLUMN_H_
24 
25 
26 //*************************************************************************************************
27 // Includes
28 //*************************************************************************************************
29 
30 #include <iterator>
31 #include <stdexcept>
39 #include <blaze/math/Forward.h>
40 #include <blaze/math/Functions.h>
42 #include <blaze/math/shims/Reset.h>
60 #include <blaze/util/Assert.h>
61 #include <blaze/util/DisableIf.h>
62 #include <blaze/util/EnableIf.h>
64 #include <blaze/util/mpl/If.h>
65 #include <blaze/util/SelectType.h>
66 #include <blaze/util/Types.h>
70 
71 
72 namespace blaze {
73 
74 //=================================================================================================
75 //
76 // CLASS DEFINITION
77 //
78 //=================================================================================================
79 
80 //*************************************************************************************************
332 template< typename MT // Type of the sparse matrix
333  , bool SO = IsColumnMajorMatrix<MT>::value > // Storage order
334 class SparseColumn : public SparseVector< SparseColumn<MT,SO>, false >
335  , private Expression
336 {
337  private:
338  //**********************************************************************************************
340 
346  enum { useConst = IsConst<MT>::value };
347  //**********************************************************************************************
348 
349  public:
350  //**Type definitions****************************************************************************
353  typedef typename ResultType::TransposeType TransposeType;
354  typedef typename MT::ElementType ElementType;
355  typedef typename MT::ReturnType ReturnType;
356  typedef const SparseColumn& CompositeType;
357 
359  typedef typename MT::ConstReference ConstReference;
360 
363 
365  typedef typename MT::ConstIterator ConstIterator;
366 
369  //**********************************************************************************************
370 
371  //**Constructors********************************************************************************
374  explicit inline SparseColumn( MT& matrix, size_t index );
375  // No explicitly declared copy constructor.
377  //**********************************************************************************************
378 
379  //**Destructor**********************************************************************************
380  // No explicitly declared destructor.
381  //**********************************************************************************************
382 
383  //**Data access functions***********************************************************************
386  inline Reference operator[]( size_t index );
387  inline ConstReference operator[]( size_t index ) const;
388  inline Iterator begin ();
389  inline ConstIterator begin () const;
390  inline ConstIterator cbegin() const;
391  inline Iterator end ();
392  inline ConstIterator end () const;
393  inline ConstIterator cend () const;
395  //**********************************************************************************************
396 
397  //**Assignment operators************************************************************************
400  inline SparseColumn& operator= ( const SparseColumn& rhs );
401  template< typename VT > inline SparseColumn& operator= ( const DenseVector <VT,false>& rhs );
402  template< typename VT > inline SparseColumn& operator= ( const SparseVector<VT,false>& rhs );
403  template< typename VT > inline SparseColumn& operator+=( const Vector<VT,false>& rhs );
404  template< typename VT > inline SparseColumn& operator-=( const Vector<VT,false>& rhs );
405  template< typename VT > inline SparseColumn& operator*=( const Vector<VT,false>& rhs );
406 
407  template< typename Other >
408  inline typename EnableIf< IsNumeric<Other>, SparseColumn >::Type&
409  operator*=( Other rhs );
410 
411  template< typename Other >
412  inline typename EnableIf< IsNumeric<Other>, SparseColumn >::Type&
413  operator/=( Other rhs );
415  //**********************************************************************************************
416 
417  //**Utility functions***************************************************************************
420  inline size_t size() const;
421  inline size_t capacity() const;
422  inline size_t nonZeros() const;
423  inline void reset();
424  inline ElementType& insert ( size_t index, const ElementType& value );
425  inline void erase ( size_t index );
426  inline Iterator erase ( Iterator pos );
427  inline Iterator find ( size_t index );
428  inline ConstIterator find ( size_t index ) const;
429  inline void reserve( size_t n );
430  template< typename Other > inline SparseColumn& scale ( Other scalar );
432  //**********************************************************************************************
433 
434  //**Low-level utility functions*****************************************************************
437  inline void append( size_t index, const ElementType& value, bool check=false );
439  //**********************************************************************************************
440 
441  //**Expression template evaluation functions****************************************************
444  template< typename Other > inline bool canAlias ( const Other* alias ) const;
445  template< typename Other > inline bool isAliased( const Other* alias ) const;
446  template< typename VT > inline void assign ( const DenseVector <VT,false>& rhs );
447  template< typename VT > inline void assign ( const SparseVector<VT,false>& rhs );
448  template< typename VT > inline void addAssign( const DenseVector <VT,false>& rhs );
449  template< typename VT > inline void addAssign( const SparseVector<VT,false>& rhs );
450  template< typename VT > inline void subAssign( const DenseVector <VT,false>& rhs );
451  template< typename VT > inline void subAssign( const SparseVector<VT,false>& rhs );
453  //**********************************************************************************************
454 
455  private:
456  //**Utility functions***************************************************************************
459  inline size_t extendCapacity() const;
461  //**********************************************************************************************
462 
463  //**Member variables****************************************************************************
466  MT& matrix_;
467  const size_t col_;
468 
469  //**********************************************************************************************
470 
471  //**Compile time checks*************************************************************************
477  //**********************************************************************************************
478 };
479 //*************************************************************************************************
480 
481 
482 
483 
484 //=================================================================================================
485 //
486 // CONSTRUCTOR
487 //
488 //=================================================================================================
489 
490 //*************************************************************************************************
497 template< typename MT // Type of the sparse matrix
498  , bool SO > // Storage order
499 inline SparseColumn<MT,SO>::SparseColumn( MT& matrix, size_t index )
500  : matrix_( matrix ) // The sparse matrix containing the column
501  , col_ ( index ) // The index of the column in the matrix
502 {
503  if( matrix_.columns() <= index )
504  throw std::invalid_argument( "Invalid column access index" );
505 }
506 //*************************************************************************************************
507 
508 
509 
510 
511 //=================================================================================================
512 //
513 // DATA ACCESS FUNCTIONS
514 //
515 //=================================================================================================
516 
517 //*************************************************************************************************
523 template< typename MT // Type of the sparse matrix
524  , bool SO > // Storage order
526 {
527  BLAZE_USER_ASSERT( index < size(), "Invalid column access index" );
528  return matrix_(index,col_);
529 }
530 //*************************************************************************************************
531 
532 
533 //*************************************************************************************************
539 template< typename MT // Type of the sparse matrix
540  , bool SO > // Storage order
542 {
543  BLAZE_USER_ASSERT( index < size(), "Invalid column access index" );
544  return const_cast<const MT&>( matrix_ )(index,col_);
545 }
546 //*************************************************************************************************
547 
548 
549 //*************************************************************************************************
556 template< typename MT // Type of the sparse matrix
557  , bool SO > // Storage order
559 {
560  return matrix_.begin( col_ );
561 }
562 //*************************************************************************************************
563 
564 
565 //*************************************************************************************************
572 template< typename MT // Type of the sparse matrix
573  , bool SO > // Storage order
575 {
576  return matrix_.begin( col_ );
577 }
578 //*************************************************************************************************
579 
580 
581 //*************************************************************************************************
588 template< typename MT // Type of the sparse matrix
589  , bool SO > // Storage order
591 {
592  return matrix_.begin( col_ );
593 }
594 //*************************************************************************************************
595 
596 
597 //*************************************************************************************************
604 template< typename MT // Type of the sparse matrix
605  , bool SO > // Storage order
607 {
608  return matrix_.end( col_ );
609 }
610 //*************************************************************************************************
611 
612 
613 //*************************************************************************************************
620 template< typename MT // Type of the sparse matrix
621  , bool SO > // Storage order
623 {
624  return matrix_.end( col_ );
625 }
626 //*************************************************************************************************
627 
628 
629 //*************************************************************************************************
636 template< typename MT // Type of the sparse matrix
637  , bool SO > // Storage order
639 {
640  return matrix_.end( col_ );
641 }
642 //*************************************************************************************************
643 
644 
645 
646 
647 //=================================================================================================
648 //
649 // ASSIGNMENT OPERATORS
650 //
651 //=================================================================================================
652 
653 //*************************************************************************************************
663 template< typename MT // Type of the sparse matrix
664  , bool SO > // Storage order
666 {
667  using blaze::assign;
668 
669  if( this == &rhs || ( &matrix_ == &rhs.matrix_ && col_ == rhs.col_ ) )
670  return *this;
671 
672  if( size() != rhs.size() )
673  throw std::invalid_argument( "Column sizes do not match" );
674 
675  if( rhs.canAlias( &matrix_ ) ) {
676  const ResultType tmp( rhs );
677  matrix_.reset ( col_ );
678  matrix_.reserve( col_, tmp.nonZeros() );
679  assign( *this, tmp );
680  }
681  else {
682  matrix_.reset ( col_ );
683  matrix_.reserve( col_, rhs.nonZeros() );
684  assign( *this, rhs );
685  }
686 
687  return *this;
688 }
689 //*************************************************************************************************
690 
691 
692 //*************************************************************************************************
702 template< typename MT // Type of the sparse matrix
703  , bool SO > // Storage order
704 template< typename VT > // Type of the right-hand side dense vector
706 {
707  using blaze::assign;
708 
709  if( size() != (~rhs).size() )
710  throw std::invalid_argument( "Vector sizes do not match" );
711 
712  if( (~rhs).canAlias( &matrix_ ) ) {
713  const typename VT::ResultType tmp( ~rhs );
714  matrix_.reset( col_ );
715  assign( *this, tmp );
716  }
717  else {
718  matrix_.reset( col_ );
719  assign( *this, ~rhs );
720  }
721 
722  return *this;
723 }
724 //*************************************************************************************************
725 
726 
727 //*************************************************************************************************
737 template< typename MT // Type of the sparse matrix
738  , bool SO > // Storage order
739 template< typename VT > // Type of the right-hand side sparse vector
741 {
742  using blaze::assign;
743 
744  if( size() != (~rhs).size() )
745  throw std::invalid_argument( "Vector sizes do not match" );
746 
747  if( (~rhs).canAlias( &matrix_ ) ) {
748  const typename VT::ResultType tmp( ~rhs );
749  matrix_.reset ( col_ );
750  matrix_.reserve( col_, tmp.nonZeros() );
751  assign( *this, tmp );
752  }
753  else {
754  matrix_.reset ( col_ );
755  matrix_.reserve( col_, (~rhs).nonZeros() );
756  assign( *this, ~rhs );
757  }
758 
759  return *this;
760 }
761 //*************************************************************************************************
762 
763 
764 //*************************************************************************************************
774 template< typename MT // Type of the sparse matrix
775  , bool SO > // Storage order
776 template< typename VT > // Type of the right-hand side vector
778 {
779  using blaze::addAssign;
780 
781  if( (~rhs).size() != size() )
782  throw std::invalid_argument( "Vector sizes do not match" );
783 
784  addAssign( *this, ~rhs );
785 
786  return *this;
787 }
788 //*************************************************************************************************
789 
790 
791 //*************************************************************************************************
801 template< typename MT // Type of the sparse matrix
802  , bool SO > // Storage order
803 template< typename VT > // Type of the right-hand side vector
805 {
806  using blaze::subAssign;
807 
808  if( (~rhs).size() != size() )
809  throw std::invalid_argument( "Vector sizes do not match" );
810 
811  subAssign( *this, ~rhs );
812 
813  return *this;
814 }
815 //*************************************************************************************************
816 
817 
818 //*************************************************************************************************
829 template< typename MT // Type of the sparse matrix
830  , bool SO > // Storage order
831 template< typename VT > // Type of the right-hand side vector
833 {
834  if( (~rhs).size() != size() )
835  throw std::invalid_argument( "Vector sizes do not match" );
836 
837  typedef typename MultTrait<This,typename VT::ResultType>::Type MultType;
838 
841 
842  const MultType tmp( *this * (~rhs) );
843  matrix_.reset( col_ );
844  assign( tmp );
845 
846  return *this;
847 }
848 //*************************************************************************************************
849 
850 
851 //*************************************************************************************************
862 template< typename MT // Type of the sparse matrix
863  , bool SO > // Storage order
864 template< typename Other > // Data type of the right-hand side scalar
865 inline typename EnableIf< IsNumeric<Other>, SparseColumn<MT,SO> >::Type&
867 {
868  for( Iterator element=begin(); element!=end(); ++element )
869  element->value() *= rhs;
870  return *this;
871 }
872 //*************************************************************************************************
873 
874 
875 //*************************************************************************************************
887 template< typename MT // Type of the sparse matrix
888  , bool SO > // Storage order
889 template< typename Other > // Data type of the right-hand side scalar
890 inline typename EnableIf< IsNumeric<Other>, SparseColumn<MT,SO> >::Type&
892 {
893  BLAZE_USER_ASSERT( rhs != Other(0), "Division by zero detected" );
894 
895  typedef typename DivTrait<ElementType,Other>::Type DT;
896  typedef typename If< IsNumeric<DT>, DT, Other >::Type Tmp;
897 
898  // Depending on the two involved data types, an integer division is applied or a
899  // floating point division is selected.
901  const Tmp tmp( Tmp(1)/static_cast<Tmp>( rhs ) );
902  for( Iterator element=begin(); element!=end(); ++element )
903  element->value() *= tmp;
904  }
905  else {
906  for( Iterator element=begin(); element!=end(); ++element )
907  element->value() /= rhs;
908  }
909 
910  return *this;
911 }
912 //*************************************************************************************************
913 
914 
915 
916 
917 //=================================================================================================
918 //
919 // UTILITY FUNCTIONS
920 //
921 //=================================================================================================
922 
923 //*************************************************************************************************
928 template< typename MT // Type of the sparse matrix
929  , bool SO > // Storage order
930 inline size_t SparseColumn<MT,SO>::size() const
931 {
932  return matrix_.rows();
933 }
934 //*************************************************************************************************
935 
936 
937 //*************************************************************************************************
942 template< typename MT // Type of the sparse matrix
943  , bool SO > // Storage order
944 inline size_t SparseColumn<MT,SO>::capacity() const
945 {
946  return matrix_.capacity( col_ );
947 }
948 //*************************************************************************************************
949 
950 
951 //*************************************************************************************************
959 template< typename MT // Type of the sparse matrix
960  , bool SO > // Storage order
961 inline size_t SparseColumn<MT,SO>::nonZeros() const
962 {
963  return matrix_.nonZeros( col_ );
964 }
965 //*************************************************************************************************
966 
967 
968 //*************************************************************************************************
973 template< typename MT // Type of the sparse matrix
974  , bool SO > // Storage order
976 {
977  matrix_.reset( col_ );
978 }
979 //*************************************************************************************************
980 
981 
982 //*************************************************************************************************
994 template< typename MT // Type of the sparse matrix
995  , bool SO > // Storage order
996 inline typename SparseColumn<MT,SO>::ElementType&
997  SparseColumn<MT,SO>::insert( size_t index, const ElementType& value )
998 {
999  return matrix_.insert( index, col_, value )->value();
1000 }
1001 //*************************************************************************************************
1002 
1003 
1004 //*************************************************************************************************
1012 template< typename MT // Type of the sparse matrix
1013  , bool SO > // Storage order
1014 inline void SparseColumn<MT,SO>::erase( size_t index )
1015 {
1016  matrix_.erase( index, col_ );
1017 }
1018 //*************************************************************************************************
1019 
1020 
1021 //*************************************************************************************************
1029 template< typename MT // Type of the sparse matrix
1030  , bool SO > // Storage order
1032 {
1033  return matrix_.erase( col_, pos );
1034 }
1035 //*************************************************************************************************
1036 
1037 
1038 //*************************************************************************************************
1051 template< typename MT // Type of the sparse matrix
1052  , bool SO > // Storage order
1054 {
1055  return matrix_.find( index, col_ );
1056 }
1057 //*************************************************************************************************
1058 
1059 
1060 //*************************************************************************************************
1073 template< typename MT // Type of the sparse matrix
1074  , bool SO > // Storage order
1076 {
1077  return matrix_.find( index, col_ );
1078 }
1079 //*************************************************************************************************
1080 
1081 
1082 //*************************************************************************************************
1091 template< typename MT // Type of the sparse matrix
1092  , bool SO > // Storage order
1094 {
1095  matrix_.reserve( col_, n );
1096 }
1097 //*************************************************************************************************
1098 
1099 
1100 //*************************************************************************************************
1106 template< typename MT // Type of the sparse matrix
1107  , bool SO > // Storage order
1108 template< typename Other > // Data type of the scalar value
1110 {
1111  for( Iterator element=begin(); element!=end(); ++element )
1112  element->value() *= scalar;
1113  return *this;
1114 }
1115 //*************************************************************************************************
1116 
1117 
1118 //*************************************************************************************************
1126 template< typename MT // Type of the sparse matrix
1127  , bool SO > // Storage order
1129 {
1130  using blaze::max;
1131  using blaze::min;
1132 
1133  size_t nonzeros( 2UL*capacity()+1UL );
1134  nonzeros = max( nonzeros, 7UL );
1135  nonzeros = min( nonzeros, size() );
1136 
1137  BLAZE_INTERNAL_ASSERT( nonzeros > capacity(), "Invalid capacity value" );
1138 
1139  return nonzeros;
1140 }
1141 //*************************************************************************************************
1142 
1143 
1144 
1145 
1146 //=================================================================================================
1147 //
1148 // LOW-LEVEL UTILITY FUNCTIONS
1149 //
1150 //=================================================================================================
1151 
1152 //*************************************************************************************************
1176 template< typename MT // Type of the sparse matrix
1177  , bool SO > // Storage order
1178 inline void SparseColumn<MT,SO>::append( size_t index, const ElementType& value, bool check )
1179 {
1180  matrix_.append( index, col_, value, check );
1181 }
1182 //*************************************************************************************************
1183 
1184 
1185 
1186 
1187 //=================================================================================================
1188 //
1189 // EXPRESSION TEMPLATE EVALUATION FUNCTIONS
1190 //
1191 //=================================================================================================
1192 
1193 //*************************************************************************************************
1203 template< typename MT // Type of the sparse matrix
1204  , bool SO > // Storage order
1205 template< typename Other > // Data type of the foreign expression
1206 inline bool SparseColumn<MT,SO>::canAlias( const Other* alias ) const
1207 {
1208  return static_cast<const void*>( &matrix_ ) == static_cast<const void*>( alias );
1209 }
1210 //*************************************************************************************************
1211 
1212 
1213 //*************************************************************************************************
1223 template< typename MT // Type of the sparse matrix
1224  , bool SO > // Storage order
1225 template< typename Other > // Data type of the foreign expression
1226 inline bool SparseColumn<MT,SO>::isAliased( const Other* alias ) const
1227 {
1228  return static_cast<const void*>( &matrix_ ) == static_cast<const void*>( alias );
1229 }
1230 //*************************************************************************************************
1231 
1232 
1233 //*************************************************************************************************
1244 template< typename MT // Type of the sparse matrix
1245  , bool SO > // Storage order
1246 template< typename VT > // Type of the right-hand side dense vector
1248 {
1249  BLAZE_INTERNAL_ASSERT( size() == (~rhs).size(), "Invalid vector sizes" );
1250 
1251  size_t nonzeros( 0UL );
1252 
1253  for( size_t i=0UL; i<size(); ++i )
1254  {
1255  if( matrix_.nonZeros( col_ ) == matrix_.capacity( col_ ) )
1256  matrix_.reserve( col_, extendCapacity() );
1257 
1258  matrix_.append( i, col_, (~rhs)[i], true );
1259  }
1260 }
1261 //*************************************************************************************************
1262 
1263 
1264 //*************************************************************************************************
1275 template< typename MT // Type of the sparse matrix
1276  , bool SO > // Storage order
1277 template< typename VT > // Type of the right-hand side sparse vector
1279 {
1280  BLAZE_INTERNAL_ASSERT( size() == (~rhs).size(), "Invalid vector sizes" );
1281 
1282  for( typename VT::ConstIterator element=(~rhs).begin(); element!=(~rhs).end(); ++element ) {
1283  matrix_.append( element->index(), col_, element->value() );
1284  }
1285 }
1286 //*************************************************************************************************
1287 
1288 
1289 //*************************************************************************************************
1300 template< typename MT // Type of the sparse matrix
1301  , bool SO > // Storage order
1302 template< typename VT > // Type of the right-hand side dense vector
1304 {
1305  typedef typename AddTrait<This,typename VT::ResultType>::Type AddType;
1306 
1310 
1311  BLAZE_INTERNAL_ASSERT( size() == (~rhs).size(), "Invalid vector sizes" );
1312 
1313  const AddType tmp( *this + (~rhs) );
1314  matrix_.reset( col_ );
1315  assign( tmp );
1316 }
1317 //*************************************************************************************************
1318 
1319 
1320 //*************************************************************************************************
1331 template< typename MT // Type of the sparse matrix
1332  , bool SO > // Storage order
1333 template< typename VT > // Type of the right-hand side sparse vector
1335 {
1336  typedef typename AddTrait<This,typename VT::ResultType>::Type AddType;
1337 
1341 
1342  BLAZE_INTERNAL_ASSERT( size() == (~rhs).size(), "Invalid vector sizes" );
1343 
1344  const AddType tmp( *this + (~rhs) );
1345  matrix_.reset ( col_ );
1346  matrix_.reserve( col_, tmp.nonZeros() );
1347  assign( tmp );
1348 }
1349 //*************************************************************************************************
1350 
1351 
1352 //*************************************************************************************************
1363 template< typename MT // Type of the sparse matrix
1364  , bool SO > // Storage order
1365 template< typename VT > // Type of the right-hand side dense vector
1367 {
1368  typedef typename SubTrait<This,typename VT::ResultType>::Type SubType;
1369 
1373 
1374  BLAZE_INTERNAL_ASSERT( size() == (~rhs).size(), "Invalid vector sizes" );
1375 
1376  const SubType tmp( *this - (~rhs) );
1377  matrix_.reset( col_ );
1378  assign( tmp );
1379 }
1380 //*************************************************************************************************
1381 
1382 
1383 //*************************************************************************************************
1394 template< typename MT // Type of the sparse matrix
1395  , bool SO > // Storage order
1396 template< typename VT > // Type of the right-hand side sparse vector
1398 {
1399  typedef typename SubTrait<This,typename VT::ResultType>::Type SubType;
1400 
1404 
1405  BLAZE_INTERNAL_ASSERT( size() == (~rhs).size(), "Invalid vector sizes" );
1406 
1407  const SubType tmp( *this - (~rhs) );
1408  matrix_.reset ( col_ );
1409  matrix_.reserve( col_, tmp.nonZeros() );
1410  assign( tmp );
1411 }
1412 //*************************************************************************************************
1413 
1414 
1415 
1416 
1417 
1418 
1419 
1420 
1421 //=================================================================================================
1422 //
1423 // CLASS TEMPLATE SPECIALIZATION FOR ROW-MAJOR MATRICES
1424 //
1425 //=================================================================================================
1426 
1427 //*************************************************************************************************
1435 template< typename MT > // Type of the sparse matrix
1436 class SparseColumn<MT,false> : public SparseVector< SparseColumn<MT,false>, false >
1437  , private Expression
1438 {
1439  private:
1440  //**********************************************************************************************
1442 
1448  enum { useConst = IsConst<MT>::value };
1449  //**********************************************************************************************
1450 
1451  public:
1452  //**Type definitions****************************************************************************
1453  typedef SparseColumn<MT,false> This;
1454  typedef typename ColumnTrait<MT>::Type ResultType;
1455  typedef typename ResultType::TransposeType TransposeType;
1456  typedef typename MT::ElementType ElementType;
1457  typedef typename MT::ReturnType ReturnType;
1458  typedef const ResultType CompositeType;
1459 
1461  typedef typename MT::ConstReference ConstReference;
1462 
1464  typedef typename SelectType< useConst, ConstReference, typename MT::Reference >::Type Reference;
1465  //**********************************************************************************************
1466 
1467  //**ColumnElement class definition**************************************************************
1470  template< typename MatrixType // Type of the sparse matrix
1471  , typename IteratorType > // Type of the sparse matrix iterator
1472  class ColumnElement
1473  {
1474  private:
1475  //*******************************************************************************************
1477 
1482  enum { returnConst = IsConst<MatrixType>::value };
1483  //*******************************************************************************************
1484 
1485  public:
1486  //**Type definitions*************************************************************************
1487  typedef typename SelectType< returnConst, const ElementType&, ElementType& >::Type ReferenceType;
1488  //*******************************************************************************************
1489 
1490  //**Constructor******************************************************************************
1496  inline ColumnElement( IteratorType pos, size_t row )
1497  : pos_( pos ) // Iterator to the current position within the sparse column
1498  , row_( row ) // Index of the according row
1499  {}
1500  //*******************************************************************************************
1501 
1502  //**Assignment operator**********************************************************************
1508  template< typename T > inline ColumnElement& operator=( const T& v ) {
1509  *pos_ = v;
1510  return *this;
1511  }
1512  //*******************************************************************************************
1513 
1514  //**Addition assignment operator*************************************************************
1520  template< typename T > inline ColumnElement& operator+=( const T& v ) {
1521  *pos_ += v;
1522  return *this;
1523  }
1524  //*******************************************************************************************
1525 
1526  //**Subtraction assignment operator**********************************************************
1532  template< typename T > inline ColumnElement& operator-=( const T& v ) {
1533  *pos_ -= v;
1534  return *this;
1535  }
1536  //*******************************************************************************************
1537 
1538  //**Multiplication assignment operator*******************************************************
1544  template< typename T > inline ColumnElement& operator*=( const T& v ) {
1545  *pos_ *= v;
1546  return *this;
1547  }
1548  //*******************************************************************************************
1549 
1550  //**Division assignment operator*************************************************************
1556  template< typename T > inline ColumnElement& operator/=( const T& v ) {
1557  *pos_ /= v;
1558  return *this;
1559  }
1560  //*******************************************************************************************
1561 
1562  //**Element access operator******************************************************************
1567  inline const ColumnElement* operator->() const {
1568  return this;
1569  }
1570  //*******************************************************************************************
1571 
1572  //**Value function***************************************************************************
1577  inline ReferenceType value() const {
1578  return pos_->value();
1579  }
1580  //*******************************************************************************************
1581 
1582  //**Index function***************************************************************************
1587  inline size_t index() const {
1588  return row_;
1589  }
1590  //*******************************************************************************************
1591 
1592  private:
1593  //**Member variables*************************************************************************
1594  IteratorType pos_;
1595  size_t row_;
1596  //*******************************************************************************************
1597  };
1598  //**********************************************************************************************
1599 
1600  //**ColumnIterator class definition*************************************************************
1603  template< typename MatrixType // Type of the sparse matrix
1604  , typename IteratorType > // Type of the sparse matrix iterator
1605  class ColumnIterator
1606  {
1607  private:
1608  //*******************************************************************************************
1610 
1615  enum { returnConst = IsConst<MatrixType>::value };
1616  //*******************************************************************************************
1617 
1618  public:
1619  //**Type definitions*************************************************************************
1620  typedef std::forward_iterator_tag IteratorCategory;
1621  typedef ColumnElement<MatrixType,IteratorType> ValueType;
1622  typedef ValueType PointerType;
1623  typedef ValueType ReferenceType;
1624  typedef ptrdiff_t DifferenceType;
1625 
1626  // STL iterator requirements
1627  typedef IteratorCategory iterator_category;
1628  typedef ValueType value_type;
1629  typedef PointerType pointer;
1630  typedef ReferenceType reference;
1631  typedef DifferenceType difference_type;
1632 
1634  typedef typename SelectType< returnConst, ReturnType, ElementType& >::Type Value;
1635  //*******************************************************************************************
1636 
1637  //**Constructor******************************************************************************
1644  inline ColumnIterator( MatrixType& matrix, size_t row, size_t column )
1645  : matrix_( matrix ) // The sparse matrix containing the column.
1646  , row_ ( row ) // The current row index.
1647  , column_( column ) // The current column index.
1648  , pos_ () // Iterator to the current sparse element.
1649  {
1650  for( ; row_<matrix_.rows(); ++row_ ) {
1651  pos_ = matrix_.find( row_, column_ );
1652  if( pos_ != matrix_.end( row_ ) ) break;
1653  }
1654  }
1655  //*******************************************************************************************
1656 
1657  //**Constructor******************************************************************************
1665  inline ColumnIterator( MatrixType& matrix, size_t row, size_t column, IteratorType pos )
1666  : matrix_( matrix ) // The sparse matrix containing the column.
1667  , row_ ( row ) // The current row index.
1668  , column_( column ) // The current column index.
1669  , pos_ ( pos ) // Iterator to the current sparse element.
1670  {
1671  BLAZE_INTERNAL_ASSERT( matrix.find( row, column ) == pos, "Invalid initial iterator position" );
1672  }
1673  //*******************************************************************************************
1674 
1675  //**Constructor******************************************************************************
1680  template< typename MatrixType2, typename IteratorType2 >
1681  inline ColumnIterator( const ColumnIterator<MatrixType2,IteratorType2>& it )
1682  : matrix_( it.matrix_ ) // The sparse matrix containing the column.
1683  , row_ ( it.row_ ) // The current row index.
1684  , column_( it.column_ ) // The current column index.
1685  , pos_ ( it.pos_ ) // Iterator to the current sparse element.
1686  {}
1687  //*******************************************************************************************
1688 
1689  //**Prefix increment operator****************************************************************
1694  inline ColumnIterator& operator++() {
1695  ++row_;
1696  for( ; row_<matrix_.rows(); ++row_ ) {
1697  pos_ = matrix_.find( row_, column_ );
1698  if( pos_ != matrix_.end( row_ ) ) break;
1699  }
1700 
1701  return *this;
1702  }
1703  //*******************************************************************************************
1704 
1705  //**Postfix increment operator***************************************************************
1710  inline const ColumnIterator operator++( int ) {
1711  const ColumnIterator tmp( *this );
1712  ++(*this);
1713  return tmp;
1714  }
1715  //*******************************************************************************************
1716 
1717  //**Element access operator******************************************************************
1722  inline ReferenceType operator*() const {
1723  return ReferenceType( pos_, row_ );
1724  }
1725  //*******************************************************************************************
1726 
1727  //**Element access operator******************************************************************
1732  inline PointerType operator->() const {
1733  return PointerType( pos_, row_ );
1734  }
1735  //*******************************************************************************************
1736 
1737  //**Equality operator************************************************************************
1743  template< typename MatrixType2, typename IteratorType2 >
1744  inline bool operator==( const ColumnIterator<MatrixType2,IteratorType2>& rhs ) const {
1745  return ( &matrix_ == &rhs.matrix_ ) && ( row_ == rhs.row_ ) && ( column_ == rhs.column_ );
1746  }
1747  //*******************************************************************************************
1748 
1749  //**Inequality operator**********************************************************************
1755  template< typename MatrixType2, typename IteratorType2 >
1756  inline bool operator!=( const ColumnIterator<MatrixType2,IteratorType2>& rhs ) const {
1757  return !( *this == rhs );
1758  }
1759  //*******************************************************************************************
1760 
1761  //**Subtraction operator*********************************************************************
1767  inline DifferenceType operator-( const ColumnIterator& rhs ) const {
1768  size_t counter( 0UL );
1769  for( size_t i=rhs.row_; i<row_; ++i ) {
1770  if( matrix_.find( i, column_ ) != matrix_.end( i ) )
1771  ++counter;
1772  }
1773  return counter;
1774  }
1775  //*******************************************************************************************
1776 
1777  private:
1778  //**Member variables*************************************************************************
1779  MatrixType& matrix_;
1780  size_t row_;
1781  size_t column_;
1782  IteratorType pos_;
1783  //*******************************************************************************************
1784 
1785  //**Friend declarations**********************************************************************
1787  template< typename MatrixType2, typename IteratorType2 > friend class ColumnIterator;
1788  template< typename MT2, bool SO2 > friend class SparseColumn;
1790  //*******************************************************************************************
1791  };
1792  //**********************************************************************************************
1793 
1794  //**Type definitions****************************************************************************
1796  typedef ColumnIterator<const MT,typename MT::ConstIterator> ConstIterator;
1797 
1799  typedef typename SelectType< useConst, ConstIterator, ColumnIterator<MT,typename MT::Iterator> >::Type Iterator;
1800  //**********************************************************************************************
1801 
1802  //**Constructors********************************************************************************
1805  explicit inline SparseColumn( MT& matrix, size_t index );
1806  // No explicitly declared copy constructor.
1808  //**********************************************************************************************
1809 
1810  //**Destructor**********************************************************************************
1811  // No explicitly declared destructor.
1812  //**********************************************************************************************
1813 
1814  //**Data access functions***********************************************************************
1817  inline Reference operator[]( size_t index );
1818  inline ConstReference operator[]( size_t index ) const;
1819  inline Iterator begin ();
1820  inline ConstIterator begin () const;
1821  inline ConstIterator cbegin() const;
1822  inline Iterator end ();
1823  inline ConstIterator end () const;
1824  inline ConstIterator cend () const;
1826  //**********************************************************************************************
1827 
1828  //**Assignment operators************************************************************************
1831  inline SparseColumn& operator= ( const SparseColumn& rhs );
1832  template< typename VT > inline SparseColumn& operator= ( const Vector<VT,false>& rhs );
1833  template< typename VT > inline SparseColumn& operator+=( const Vector<VT,false>& rhs );
1834  template< typename VT > inline SparseColumn& operator-=( const Vector<VT,false>& rhs );
1835  template< typename VT > inline SparseColumn& operator*=( const Vector<VT,false>& rhs );
1836 
1837  template< typename Other >
1838  inline typename EnableIf< IsNumeric<Other>, SparseColumn >::Type&
1839  operator*=( Other rhs );
1840 
1841  template< typename Other >
1842  inline typename EnableIf< IsNumeric<Other>, SparseColumn >::Type&
1843  operator/=( Other rhs );
1845  //**********************************************************************************************
1846 
1847  //**Utility functions***************************************************************************
1850  inline size_t size() const;
1851  inline size_t capacity() const;
1852  inline size_t nonZeros() const;
1853  inline void reset();
1854  inline ElementType& insert ( size_t index, const ElementType& value );
1855  inline void erase ( size_t index );
1856  inline Iterator erase ( Iterator pos );
1857  inline Iterator find ( size_t index );
1858  inline ConstIterator find ( size_t index ) const;
1859  inline void reserve( size_t n );
1860  template< typename Other > inline SparseColumn& scale ( Other scalar );
1862  //**********************************************************************************************
1863 
1864  //**Low-level utility functions*****************************************************************
1867  inline void append( size_t index, const ElementType& value, bool check=false );
1869  //**********************************************************************************************
1870 
1871  //**Expression template evaluation functions****************************************************
1874  template< typename Other > inline bool canAlias ( const Other* alias ) const;
1875  template< typename Other > inline bool isAliased( const Other* alias ) const;
1876  template< typename VT > inline void assign ( const DenseVector <VT,false>& rhs );
1877  template< typename VT > inline void assign ( const SparseVector<VT,false>& rhs );
1878  template< typename VT > inline void addAssign( const Vector<VT,false>& rhs );
1879  template< typename VT > inline void subAssign( const Vector<VT,false>& rhs );
1881  //**********************************************************************************************
1882 
1883  private:
1884  //**Member variables****************************************************************************
1887  MT& matrix_;
1888  const size_t col_;
1889 
1890  //**********************************************************************************************
1891 
1892  //**Compile time checks*************************************************************************
1898  //**********************************************************************************************
1899 };
1901 //*************************************************************************************************
1902 
1903 
1904 
1905 
1906 //=================================================================================================
1907 //
1908 // CONSTRUCTOR
1909 //
1910 //=================================================================================================
1911 
1912 //*************************************************************************************************
1920 template< typename MT > // Type of the sparse matrix
1921 inline SparseColumn<MT,false>::SparseColumn( MT& matrix, size_t index )
1922  : matrix_( matrix ) // The sparse matrix containing the column
1923  , col_ ( index ) // The index of the column in the matrix
1924 {
1925  if( matrix_.columns() <= index )
1926  throw std::invalid_argument( "Invalid column access index" );
1927 }
1929 //*************************************************************************************************
1930 
1931 
1932 
1933 
1934 //=================================================================================================
1935 //
1936 // DATA ACCESS FUNCTIONS
1937 //
1938 //=================================================================================================
1939 
1940 //*************************************************************************************************
1947 template< typename MT > // Type of the sparse matrix
1948 inline typename SparseColumn<MT,false>::Reference SparseColumn<MT,false>::operator[]( size_t index )
1949 {
1950  BLAZE_USER_ASSERT( index < size(), "Invalid column access index" );
1951  return matrix_(index,col_);
1952 }
1954 //*************************************************************************************************
1955 
1956 
1957 //*************************************************************************************************
1964 template< typename MT > // Type of the sparse matrix
1965 inline typename SparseColumn<MT,false>::ConstReference SparseColumn<MT,false>::operator[]( size_t index ) const
1966 {
1967  BLAZE_USER_ASSERT( index < size(), "Invalid column access index" );
1968  return const_cast<const MT&>( matrix_ )(index,col_);
1969 }
1971 //*************************************************************************************************
1972 
1973 
1974 //*************************************************************************************************
1982 template< typename MT > // Type of the sparse matrix
1983 inline typename SparseColumn<MT,false>::Iterator SparseColumn<MT,false>::begin()
1984 {
1985  return Iterator( matrix_, 0UL, col_ );
1986 }
1988 //*************************************************************************************************
1989 
1990 
1991 //*************************************************************************************************
1999 template< typename MT > // Type of the sparse matrix
2000 inline typename SparseColumn<MT,false>::ConstIterator SparseColumn<MT,false>::begin() const
2001 {
2002  return ConstIterator( matrix_, 0UL, col_ );
2003 }
2005 //*************************************************************************************************
2006 
2007 
2008 //*************************************************************************************************
2016 template< typename MT > // Type of the sparse matrix
2017 inline typename SparseColumn<MT,false>::ConstIterator SparseColumn<MT,false>::cbegin() const
2018 {
2019  return ConstIterator( matrix_, 0UL, col_ );
2020 }
2022 //*************************************************************************************************
2023 
2024 
2025 //*************************************************************************************************
2033 template< typename MT > // Type of the sparse matrix
2034 inline typename SparseColumn<MT,false>::Iterator SparseColumn<MT,false>::end()
2035 {
2036  return Iterator( matrix_, size(), col_ );
2037 }
2039 //*************************************************************************************************
2040 
2041 
2042 //*************************************************************************************************
2050 template< typename MT > // Type of the sparse matrix
2051 inline typename SparseColumn<MT,false>::ConstIterator SparseColumn<MT,false>::end() const
2052 {
2053  return ConstIterator( matrix_, size(), col_ );
2054 }
2056 //*************************************************************************************************
2057 
2058 
2059 //*************************************************************************************************
2067 template< typename MT > // Type of the sparse matrix
2068 inline typename SparseColumn<MT,false>::ConstIterator SparseColumn<MT,false>::cend() const
2069 {
2070  return ConstIterator( matrix_, size(), col_ );
2071 }
2073 //*************************************************************************************************
2074 
2075 
2076 
2077 
2078 //=================================================================================================
2079 //
2080 // ASSIGNMENT OPERATORS
2081 //
2082 //=================================================================================================
2083 
2084 //*************************************************************************************************
2095 template< typename MT > // Type of the sparse matrix
2096 inline SparseColumn<MT,false>& SparseColumn<MT,false>::operator=( const SparseColumn& rhs )
2097 {
2098  using blaze::assign;
2099 
2100  if( this == &rhs || ( &matrix_ == &rhs.matrix_ && col_ == rhs.col_ ) )
2101  return *this;
2102 
2103  if( size() != rhs.size() )
2104  throw std::invalid_argument( "Column sizes do not match" );
2105 
2106  if( rhs.canAlias( &matrix_ ) ) {
2107  const ResultType tmp( rhs );
2108  assign( *this, tmp );
2109  }
2110  else {
2111  assign( *this, rhs );
2112  }
2113 
2114  return *this;
2115 }
2117 //*************************************************************************************************
2118 
2119 
2120 //*************************************************************************************************
2131 template< typename MT > // Type of the sparse matrix
2132 template< typename VT > // Type of the right-hand side vector
2133 inline SparseColumn<MT,false>& SparseColumn<MT,false>::operator=( const Vector<VT,false>& rhs )
2134 {
2135  using blaze::assign;
2136 
2137  if( size() != (~rhs).size() )
2138  throw std::invalid_argument( "Vector sizes do not match" );
2139 
2140  const typename VT::CompositeType tmp( ~rhs );
2141  assign( *this, tmp );
2142 
2143  return *this;
2144 }
2146 //*************************************************************************************************
2147 
2148 
2149 //*************************************************************************************************
2160 template< typename MT > // Type of the sparse matrix
2161 template< typename VT > // Type of the right-hand side vector
2162 inline SparseColumn<MT,false>& SparseColumn<MT,false>::operator+=( const Vector<VT,false>& rhs )
2163 {
2164  using blaze::addAssign;
2165 
2166  if( (~rhs).size() != size() )
2167  throw std::invalid_argument( "Vector sizes do not match" );
2168 
2169  addAssign( *this, ~rhs );
2170 
2171  return *this;
2172 }
2174 //*************************************************************************************************
2175 
2176 
2177 //*************************************************************************************************
2188 template< typename MT > // Type of the sparse matrix
2189 template< typename VT > // Type of the right-hand side vector
2190 inline SparseColumn<MT,false>& SparseColumn<MT,false>::operator-=( const Vector<VT,false>& rhs )
2191 {
2192  using blaze::subAssign;
2193 
2194  if( (~rhs).size() != size() )
2195  throw std::invalid_argument( "Vector sizes do not match" );
2196 
2197  subAssign( *this, ~rhs );
2198 
2199  return *this;
2200 }
2202 //*************************************************************************************************
2203 
2204 
2205 //*************************************************************************************************
2217 template< typename MT > // Type of the sparse matrix
2218 template< typename VT > // Type of the right-hand side vector
2219 inline SparseColumn<MT,false>& SparseColumn<MT,false>::operator*=( const Vector<VT,false>& rhs )
2220 {
2221  if( (~rhs).size() != size() )
2222  throw std::invalid_argument( "Vector sizes do not match" );
2223 
2224  typedef typename MultTrait<This,typename VT::ResultType>::Type MultType;
2225 
2228 
2229  const MultType tmp( *this * (~rhs) );
2230  assign( tmp );
2231 
2232  return *this;
2233 }
2235 //*************************************************************************************************
2236 
2237 
2238 //*************************************************************************************************
2250 template< typename MT > // Type of the sparse matrix
2251 template< typename Other > // Data type of the right-hand side scalar
2252 inline typename EnableIf< IsNumeric<Other>, SparseColumn<MT,false> >::Type&
2253  SparseColumn<MT,false>::operator*=( Other rhs )
2254 {
2255  for( Iterator element=begin(); element!=end(); ++element )
2256  element->value() *= rhs;
2257  return *this;
2258 }
2260 //*************************************************************************************************
2261 
2262 
2263 //*************************************************************************************************
2276 template< typename MT > // Type of the sparse matrix
2277 template< typename Other > // Data type of the right-hand side scalar
2278 inline typename EnableIf< IsNumeric<Other>, SparseColumn<MT,false> >::Type&
2279  SparseColumn<MT,false>::operator/=( Other rhs )
2280 {
2281  BLAZE_USER_ASSERT( rhs != Other(0), "Division by zero detected" );
2282 
2283  typedef typename DivTrait<ElementType,Other>::Type DT;
2284  typedef typename If< IsNumeric<DT>, DT, Other >::Type Tmp;
2285 
2286  // Depending on the two involved data types, an integer division is applied or a
2287  // floating point division is selected.
2288  if( IsNumeric<DT>::value && IsFloatingPoint<DT>::value ) {
2289  const Tmp tmp( Tmp(1)/static_cast<Tmp>( rhs ) );
2290  for( Iterator element=begin(); element!=end(); ++element )
2291  element->value() *= tmp;
2292  }
2293  else {
2294  for( Iterator element=begin(); element!=end(); ++element )
2295  element->value() /= rhs;
2296  }
2297 
2298  return *this;
2299 }
2301 //*************************************************************************************************
2302 
2303 
2304 
2305 
2306 //=================================================================================================
2307 //
2308 // UTILITY FUNCTIONS
2309 //
2310 //=================================================================================================
2311 
2312 //*************************************************************************************************
2318 template< typename MT > // Type of the sparse matrix
2319 inline size_t SparseColumn<MT,false>::size() const
2320 {
2321  return matrix_.rows();
2322 }
2324 //*************************************************************************************************
2325 
2326 
2327 //*************************************************************************************************
2333 template< typename MT > // Type of the sparse matrix
2334 inline size_t SparseColumn<MT,false>::capacity() const
2335 {
2336  return matrix_.rows();
2337 }
2339 //*************************************************************************************************
2340 
2341 
2342 //*************************************************************************************************
2351 template< typename MT > // Type of the sparse matrix
2352 inline size_t SparseColumn<MT,false>::nonZeros() const
2353 {
2354  size_t counter( 0UL );
2355  for( ConstIterator element=begin(); element!=end(); ++element ) {
2356  ++counter;
2357  }
2358  return counter;
2359 }
2361 //*************************************************************************************************
2362 
2363 
2364 //*************************************************************************************************
2370 template< typename MT > // Type of the sparse matrix
2371 inline void SparseColumn<MT,false>::reset()
2372 {
2373  for( size_t i=0UL; i<size(); ++i ) {
2374  matrix_.erase( i, col_ );
2375  }
2376 }
2378 //*************************************************************************************************
2379 
2380 
2381 //*************************************************************************************************
2394 template< typename MT > // Type of the sparse matrix
2395 inline typename SparseColumn<MT,false>::ElementType&
2396  SparseColumn<MT,false>::insert( size_t index, const ElementType& value )
2397 {
2398  return matrix_.insert( index, col_, value )->value();
2399 }
2401 //*************************************************************************************************
2402 
2403 
2404 //*************************************************************************************************
2413 template< typename MT > // Type of the sparse matrix
2414 inline void SparseColumn<MT,false>::erase( size_t index )
2415 {
2416  matrix_.erase( index, col_ );
2417 }
2419 //*************************************************************************************************
2420 
2421 
2422 //*************************************************************************************************
2431 template< typename MT > // Type of the sparse matrix
2432 inline typename SparseColumn<MT,false>::Iterator SparseColumn<MT,false>::erase( Iterator pos )
2433 {
2434  const size_t row( pos.row_ );
2435 
2436  if( row == size() )
2437  return pos;
2438 
2439  matrix_.erase( row, pos.pos_ );
2440  return Iterator( matrix_, row+1UL, col_ );
2441 }
2443 //*************************************************************************************************
2444 
2445 
2446 //*************************************************************************************************
2460 template< typename MT > // Type of the sparse matrix
2461 inline typename SparseColumn<MT,false>::Iterator SparseColumn<MT,false>::find( size_t index )
2462 {
2463  const typename MT::Iterator pos( matrix_.find( index, col_ ) );
2464 
2465  if( pos != matrix_.end( index ) )
2466  return Iterator( matrix_, index, col_, pos );
2467  else
2468  return end();
2469 }
2471 //*************************************************************************************************
2472 
2473 
2474 //*************************************************************************************************
2488 template< typename MT > // Type of the sparse matrix
2489 inline typename SparseColumn<MT,false>::ConstIterator SparseColumn<MT,false>::find( size_t index ) const
2490 {
2491  const typename MT::ConstIterator pos( matrix_.find( index, col_ ) );
2492 
2493  if( pos != matrix_.end( index ) )
2494  return ConstIterator( matrix_, index, col_, pos );
2495  else
2496  return end();
2497 }
2499 //*************************************************************************************************
2500 
2501 
2502 //*************************************************************************************************
2512 template< typename MT > // Type of the sparse matrix
2513 void SparseColumn<MT,false>::reserve( size_t n )
2514 {
2515  return;
2516 }
2518 //*************************************************************************************************
2519 
2520 
2521 //*************************************************************************************************
2528 template< typename MT > // Type of the sparse matrix
2529 template< typename Other > // Data type of the scalar value
2530 inline SparseColumn<MT,false>& SparseColumn<MT,false>::scale( Other scalar )
2531 {
2532  for( Iterator element=begin(); element!=end(); ++element )
2533  element->value() *= scalar;
2534  return *this;
2535 }
2537 //*************************************************************************************************
2538 
2539 
2540 
2541 
2542 //=================================================================================================
2543 //
2544 // LOW-LEVEL UTILITY FUNCTIONS
2545 //
2546 //=================================================================================================
2547 
2548 //*************************************************************************************************
2573 template< typename MT > // Type of the sparse matrix
2574 inline void SparseColumn<MT,false>::append( size_t index, const ElementType& value, bool /*check*/ )
2575 {
2576  matrix_.insert( index, col_, value );
2577 }
2579 //*************************************************************************************************
2580 
2581 
2582 
2583 
2584 //=================================================================================================
2585 //
2586 // EXPRESSION TEMPLATE EVALUATION FUNCTIONS
2587 //
2588 //=================================================================================================
2589 
2590 //*************************************************************************************************
2601 template< typename MT > // Type of the sparse matrix
2602 template< typename Other > // Data type of the foreign expression
2603 inline bool SparseColumn<MT,false>::canAlias( const Other* alias ) const
2604 {
2605  return static_cast<const void*>( &matrix_ ) == static_cast<const void*>( alias );
2606 }
2608 //*************************************************************************************************
2609 
2610 
2611 //*************************************************************************************************
2618 template< typename MT > // Type of the sparse matrix
2619 template< typename Other > // Data type of the foreign expression
2620 inline bool SparseColumn<MT,false>::isAliased( const Other* alias ) const
2621 {
2622  return static_cast<const void*>( &matrix_ ) == static_cast<const void*>( alias );
2623 }
2625 //*************************************************************************************************
2626 
2627 
2628 //*************************************************************************************************
2640 template< typename MT > // Type of the sparse matrix
2641 template< typename VT > // Type of the right-hand side dense vector
2642 inline void SparseColumn<MT,false>::assign( const DenseVector<VT,false>& rhs )
2643 {
2644  BLAZE_INTERNAL_ASSERT( size() == (~rhs).size(), "Invalid vector sizes" );
2645 
2646  for( size_t i=0UL; i<(~rhs).size(); ++i ) {
2647  matrix_(i,col_) = (~rhs)[i];
2648  }
2649 }
2651 //*************************************************************************************************
2652 
2653 
2654 //*************************************************************************************************
2666 template< typename MT > // Type of the sparse matrix
2667 template< typename VT > // Type of the right-hand side sparse vector
2668 inline void SparseColumn<MT,false>::assign( const SparseVector<VT,false>& rhs )
2669 {
2670  BLAZE_INTERNAL_ASSERT( size() == (~rhs).size(), "Invalid vector sizes" );
2671 
2672  size_t i( 0UL );
2673 
2674  for( typename VT::ConstIterator element=(~rhs).begin(); element!=(~rhs).end(); ++element ) {
2675  for( ; i<element->index(); ++i )
2676  matrix_.erase( i, col_ );
2677  matrix_(i++,col_) = element->value();
2678  }
2679  for( ; i<size(); ++i ) {
2680  matrix_.erase( i, col_ );
2681  }
2682 }
2684 //*************************************************************************************************
2685 
2686 
2687 //*************************************************************************************************
2699 template< typename MT > // Type of the sparse matrix
2700 template< typename VT > // Type of the right-hand side vector
2701 inline void SparseColumn<MT,false>::addAssign( const Vector<VT,false>& rhs )
2702 {
2703  typedef typename AddTrait<This,typename VT::ResultType>::Type AddType;
2704 
2707 
2708  BLAZE_INTERNAL_ASSERT( size() == (~rhs).size(), "Invalid vector sizes" );
2709 
2710  const AddType tmp( *this + (~rhs) );
2711  assign( tmp );
2712 }
2714 //*************************************************************************************************
2715 
2716 
2717 //*************************************************************************************************
2729 template< typename MT > // Type of the sparse matrix
2730 template< typename VT > // Type of the right-hand side vector
2731 inline void SparseColumn<MT,false>::subAssign( const Vector<VT,false>& rhs )
2732 {
2733  typedef typename SubTrait<This,typename VT::ResultType>::Type SubType;
2734 
2737 
2738  BLAZE_INTERNAL_ASSERT( size() == (~rhs).size(), "Invalid vector sizes" );
2739 
2740  const SubType tmp( *this - (~rhs) );
2741  assign( tmp );
2742 }
2744 //*************************************************************************************************
2745 
2746 
2747 
2748 
2749 
2750 
2751 
2752 
2753 //=================================================================================================
2754 //
2755 // SPARSECOLUMN OPERATORS
2756 //
2757 //=================================================================================================
2758 
2759 //*************************************************************************************************
2762 template< typename MT, bool SO >
2763 inline void reset( SparseColumn<MT,SO>& column );
2764 
2765 template< typename MT, bool SO >
2766 inline void clear( SparseColumn<MT,SO>& column );
2767 
2768 template< typename MT, bool SO >
2769 inline bool isnan( const SparseColumn<MT,SO>& column );
2770 
2771 template< typename MT, bool SO >
2772 inline bool isDefault( const SparseColumn<MT,SO>& column );
2774 //*************************************************************************************************
2775 
2776 
2777 //*************************************************************************************************
2784 template< typename MT // Type of the sparse matrix
2785  , bool SO > // Storage order
2786 inline void reset( SparseColumn<MT,SO>& column )
2787 {
2788  column.reset();
2789 }
2790 //*************************************************************************************************
2791 
2792 
2793 //*************************************************************************************************
2800 template< typename MT // Type of the sparse matrix
2801  , bool SO > // Storage order
2802 inline void clear( SparseColumn<MT,SO>& column )
2803 {
2804  column.reset();
2805 }
2806 //*************************************************************************************************
2807 
2808 
2809 //*************************************************************************************************
2825 template< typename MT // Type of the sparse matrix
2826  , bool SO > // Storage order
2827 inline bool isnan( const SparseColumn<MT,SO>& column )
2828 {
2829  typedef typename SparseColumn<MT,SO>::ConstIterator ConstIterator;
2830 
2831  const ConstIterator end( column.end() );
2832  for( ConstIterator element=column.begin(); element!=end; ++element ) {
2833  if( isnan( element->value() ) ) return true;
2834  }
2835  return false;
2836 }
2837 //*************************************************************************************************
2838 
2839 
2840 //*************************************************************************************************
2858 template< typename MT // Type of the sparse matrix
2859  , bool SO > // Storage order
2860 inline bool isDefault( const SparseColumn<MT,SO>& column )
2861 {
2862  typedef typename SparseColumn<MT,SO>::ConstIterator ConstIterator;
2863 
2864  const ConstIterator end( column.end() );
2865  for( ConstIterator element=column.begin(); element!=end; ++element )
2866  if( !isDefault( element->value() ) ) return false;
2867  return true;
2868 }
2869 //*************************************************************************************************
2870 
2871 
2872 
2873 
2874 //=================================================================================================
2875 //
2876 // GLOBAL OPERATORS
2877 //
2878 //=================================================================================================
2879 
2880 //*************************************************************************************************
2899 template< typename MT // Type of the sparse matrix
2900  , bool SO > // Storage order
2901 inline typename DisableIf< IsExpression<MT>, SparseColumn<MT> >::Type
2902  column( SparseMatrix<MT,SO>& sm, size_t index )
2903 {
2905 
2906  return SparseColumn<MT>( ~sm, index );
2907 }
2908 //*************************************************************************************************
2909 
2910 
2911 //*************************************************************************************************
2930 template< typename MT // Type of the sparse matrix
2931  , bool SO > // Storage order
2932 inline typename DisableIf< IsExpression<MT>, SparseColumn<const MT> >::Type
2933  column( const SparseMatrix<MT,SO>& sm, size_t index )
2934 {
2936 
2937  return SparseColumn<const MT>( ~sm, index );
2938 }
2939 //*************************************************************************************************
2940 
2941 
2942 
2943 
2944 //=================================================================================================
2945 //
2946 // GLOBAL RESTRUCTURING OPERATORS
2947 //
2948 //=================================================================================================
2949 
2950 //*************************************************************************************************
2962 template< typename MT // Type of the sparse matrix
2963  , bool SO > // Storage order
2964 inline typename EnableIf< IsMatMatAddExpr<MT>, typename ColumnExprTrait<MT>::Type >::Type
2965  column( const SparseMatrix<MT,SO>& dm, size_t index )
2966 {
2968 
2969  return column( (~dm).leftOperand(), index ) + column( (~dm).rightOperand(), index );
2970 }
2972 //*************************************************************************************************
2973 
2974 
2975 //*************************************************************************************************
2987 template< typename MT // Type of the sparse matrix
2988  , bool SO > // Storage order
2989 inline typename EnableIf< IsMatMatSubExpr<MT>, typename ColumnExprTrait<MT>::Type >::Type
2990  column( const SparseMatrix<MT,SO>& dm, size_t index )
2991 {
2993 
2994  return column( (~dm).leftOperand(), index ) - column( (~dm).rightOperand(), index );
2995 }
2997 //*************************************************************************************************
2998 
2999 
3000 //*************************************************************************************************
3012 template< typename MT // Type of the sparse matrix
3013  , bool SO > // Storage order
3014 inline typename EnableIf< IsMatMatMultExpr<MT>, typename ColumnExprTrait<MT>::Type >::Type
3015  column( const SparseMatrix<MT,SO>& dm, size_t index )
3016 {
3018 
3019  return (~dm).leftOperand() * column( (~dm).rightOperand(), index );
3020 }
3022 //*************************************************************************************************
3023 
3024 
3025 //*************************************************************************************************
3037 template< typename MT // Type of the sparse matrix
3038  , bool SO > // Storage order
3039 inline typename EnableIf< IsVecTVecMultExpr<MT>, typename ColumnExprTrait<MT>::Type >::Type
3040  column( const SparseMatrix<MT,SO>& dm, size_t index )
3041 {
3043 
3044  return (~dm).leftOperand() * (~dm).rightOperand()[index];
3045 }
3047 //*************************************************************************************************
3048 
3049 
3050 //*************************************************************************************************
3062 template< typename MT // Type of the sparse matrix
3063  , bool SO > // Storage order
3064 inline typename EnableIf< IsMatScalarMultExpr<MT>, typename ColumnExprTrait<MT>::Type >::Type
3065  column( const SparseMatrix<MT,SO>& dm, size_t index )
3066 {
3068 
3069  return column( (~dm).leftOperand(), index ) * (~dm).rightOperand();
3070 }
3072 //*************************************************************************************************
3073 
3074 
3075 //*************************************************************************************************
3087 template< typename MT // Type of the sparse matrix
3088  , bool SO > // Storage order
3089 inline typename EnableIf< IsMatScalarDivExpr<MT>, typename ColumnExprTrait<MT>::Type >::Type
3090  column( const SparseMatrix<MT,SO>& dm, size_t index )
3091 {
3093 
3094  return column( (~dm).leftOperand(), index ) / (~dm).rightOperand();
3095 }
3097 //*************************************************************************************************
3098 
3099 
3100 //*************************************************************************************************
3112 template< typename MT // Type of the sparse matrix
3113  , bool SO > // Storage order
3114 inline typename EnableIf< IsMatAbsExpr<MT>, typename ColumnExprTrait<MT>::Type >::Type
3115  column( const SparseMatrix<MT,SO>& dm, size_t index )
3116 {
3118 
3119  return abs( column( (~dm).operand(), index ) );
3120 }
3122 //*************************************************************************************************
3123 
3124 
3125 //*************************************************************************************************
3137 template< typename MT // Type of the sparse matrix
3138  , bool SO > // Storage order
3139 inline typename EnableIf< IsMatEvalExpr<MT>, typename ColumnExprTrait<MT>::Type >::Type
3140  column( const SparseMatrix<MT,SO>& dm, size_t index )
3141 {
3143 
3144  return eval( column( (~dm).operand(), index ) );
3145 }
3147 //*************************************************************************************************
3148 
3149 
3150 //*************************************************************************************************
3162 template< typename MT // Type of the sparse matrix
3163  , bool SO > // Storage order
3164 inline typename EnableIf< IsMatTransExpr<MT>, typename ColumnExprTrait<MT>::Type >::Type
3165  column( const SparseMatrix<MT,SO>& dm, size_t index )
3166 {
3168 
3169  return trans( row( (~dm).operand(), index ) );
3170 }
3172 //*************************************************************************************************
3173 
3174 
3175 
3176 
3177 //=================================================================================================
3178 //
3179 // ADDTRAIT SPECIALIZATIONS
3180 //
3181 //=================================================================================================
3182 
3183 //*************************************************************************************************
3185 template< typename T1, bool SO, typename T2, size_t N >
3186 struct AddTrait< SparseColumn<T1,SO>, StaticVector<T2,N,false> >
3187 {
3188  typedef typename AddTrait< typename SparseColumn<T1,SO>::ResultType,
3189  StaticVector<T2,N,false> >::Type Type;
3190 };
3191 
3192 template< typename T1, size_t N, typename T2, bool SO >
3193 struct AddTrait< StaticVector<T1,N,false>, SparseColumn<T2,SO> >
3194 {
3195  typedef typename AddTrait< StaticVector<T1,N,false>,
3196  typename SparseColumn<T2,SO>::ResultType >::Type Type;
3197 };
3198 
3199 template< typename T1, bool SO, typename T2 >
3200 struct AddTrait< SparseColumn<T1,SO>, DynamicVector<T2,false> >
3201 {
3202  typedef typename AddTrait< typename SparseColumn<T1,SO>::ResultType,
3203  DynamicVector<T2,false> >::Type Type;
3204 };
3205 
3206 template< typename T1, typename T2, bool SO >
3207 struct AddTrait< DynamicVector<T1,false>, SparseColumn<T2,SO> >
3208 {
3209  typedef typename AddTrait< DynamicVector<T1,false>,
3210  typename SparseColumn<T2,SO>::ResultType >::Type Type;
3211 };
3212 
3213 template< typename T1, bool SO1, typename T2, bool SO2 >
3214 struct AddTrait< SparseColumn<T1,SO1>, DenseColumn<T2,SO2> >
3215 {
3216  typedef typename AddTrait< typename SparseColumn<T1,SO1>::ResultType,
3217  typename DenseColumn <T2,SO2>::ResultType >::Type Type;
3218 };
3219 
3220 template< typename T1, bool SO1, typename T2, bool SO2 >
3221 struct AddTrait< DenseColumn<T1,SO1>, SparseColumn<T2,SO2> >
3222 {
3223  typedef typename AddTrait< typename DenseColumn <T1,SO1>::ResultType,
3224  typename SparseColumn<T2,SO2>::ResultType >::Type Type;
3225 };
3226 
3227 template< typename T1, bool SO, typename T2 >
3228 struct AddTrait< SparseColumn<T1,SO>, CompressedVector<T2,false> >
3229 {
3230  typedef typename AddTrait< typename SparseColumn<T1,SO>::ResultType,
3231  CompressedVector<T2,false> >::Type Type;
3232 };
3233 
3234 template< typename T1, typename T2, bool SO >
3235 struct AddTrait< CompressedVector<T1,false>, SparseColumn<T2,SO> >
3236 {
3237  typedef typename AddTrait< CompressedVector<T1,false>,
3238  typename SparseColumn<T2,SO>::ResultType >::Type Type;
3239 };
3240 
3241 template< typename T1, bool SO1, typename T2, bool SO2 >
3242 struct AddTrait< SparseColumn<T1,SO1>, SparseColumn<T2,SO2> >
3243 {
3244  typedef typename AddTrait< typename SparseColumn<T1,SO1>::ResultType,
3245  typename SparseColumn<T2,SO2>::ResultType >::Type Type;
3246 };
3248 //*************************************************************************************************
3249 
3250 
3251 
3252 
3253 //=================================================================================================
3254 //
3255 // SUBTRAIT SPECIALIZATIONS
3256 //
3257 //=================================================================================================
3258 
3259 //*************************************************************************************************
3261 template< typename T1, bool SO, typename T2, size_t N >
3262 struct SubTrait< SparseColumn<T1,SO>, StaticVector<T2,N,false> >
3263 {
3264  typedef typename SubTrait< typename SparseColumn<T1,SO>::ResultType,
3265  StaticVector<T2,N,false> >::Type Type;
3266 };
3267 
3268 template< typename T1, size_t N, typename T2, bool SO >
3269 struct SubTrait< StaticVector<T1,N,false>, SparseColumn<T2,SO> >
3270 {
3271  typedef typename SubTrait< StaticVector<T1,N,false>,
3272  typename SparseColumn<T2,SO>::ResultType >::Type Type;
3273 };
3274 
3275 template< typename T1, bool SO, typename T2 >
3276 struct SubTrait< SparseColumn<T1,SO>, DynamicVector<T2,false> >
3277 {
3278  typedef typename SubTrait< typename SparseColumn<T1,SO>::ResultType,
3279  DynamicVector<T2,false> >::Type Type;
3280 };
3281 
3282 template< typename T1, typename T2, bool SO >
3283 struct SubTrait< DynamicVector<T1,false>, SparseColumn<T2,SO> >
3284 {
3285  typedef typename SubTrait< DynamicVector<T1,false>,
3286  typename SparseColumn<T2,SO>::ResultType >::Type Type;
3287 };
3288 
3289 template< typename T1, bool SO1, typename T2, bool SO2 >
3290 struct SubTrait< SparseColumn<T1,SO1>, DenseColumn<T2,SO2> >
3291 {
3292  typedef typename SubTrait< typename SparseColumn<T1,SO1>::ResultType,
3293  typename DenseColumn <T2,SO2>::ResultType >::Type Type;
3294 };
3295 
3296 template< typename T1, bool SO1, typename T2, bool SO2 >
3297 struct SubTrait< DenseColumn<T1,SO1>, SparseColumn<T2,SO2> >
3298 {
3299  typedef typename SubTrait< typename DenseColumn <T1,SO1>::ResultType,
3300  typename SparseColumn<T2,SO2>::ResultType >::Type Type;
3301 };
3302 
3303 template< typename T1, bool SO, typename T2 >
3304 struct SubTrait< SparseColumn<T1,SO>, CompressedVector<T2,false> >
3305 {
3306  typedef typename SubTrait< typename SparseColumn<T1,SO>::ResultType,
3307  CompressedVector<T2,false> >::Type Type;
3308 };
3309 
3310 template< typename T1, typename T2, bool SO >
3311 struct SubTrait< CompressedVector<T1,false>, SparseColumn<T2,SO> >
3312 {
3313  typedef typename SubTrait< CompressedVector<T1,false>,
3314  typename SparseColumn<T2,SO>::ResultType >::Type Type;
3315 };
3316 
3317 template< typename T1, bool SO1, typename T2, bool SO2 >
3318 struct SubTrait< SparseColumn<T1,SO1>, SparseColumn<T2,SO2> >
3319 {
3320  typedef typename SubTrait< typename SparseColumn<T1,SO1>::ResultType,
3321  typename SparseColumn<T2,SO2>::ResultType >::Type Type;
3322 };
3324 //*************************************************************************************************
3325 
3326 
3327 
3328 
3329 //=================================================================================================
3330 //
3331 // MULTTRAIT SPECIALIZATIONS
3332 //
3333 //=================================================================================================
3334 
3335 //*************************************************************************************************
3337 template< typename T1, bool SO, typename T2 >
3338 struct MultTrait< SparseColumn<T1,SO>, T2 >
3339 {
3340  typedef typename MultTrait< typename SparseColumn<T1,SO>::ResultType, T2 >::Type Type;
3342 };
3343 
3344 template< typename T1, typename T2, bool SO >
3345 struct MultTrait< T1, SparseColumn<T2,SO> >
3346 {
3347  typedef typename MultTrait< T1, typename SparseColumn<T2,SO>::ResultType >::Type Type;
3349 };
3350 
3351 template< typename T1, bool SO, typename T2, size_t N, bool TF >
3352 struct MultTrait< SparseColumn<T1,SO>, StaticVector<T2,N,TF> >
3353 {
3354  typedef typename MultTrait< typename SparseColumn<T1,SO>::ResultType,
3355  StaticVector<T2,N,TF> >::Type Type;
3356 };
3357 
3358 template< typename T1, size_t N, bool TF, typename T2, bool SO >
3359 struct MultTrait< StaticVector<T1,N,TF>, SparseColumn<T2,SO> >
3360 {
3361  typedef typename MultTrait< StaticVector<T1,N,TF>,
3362  typename SparseColumn<T2,SO>::ResultType >::Type Type;
3363 };
3364 
3365 template< typename T1, bool SO, typename T2, bool TF >
3366 struct MultTrait< SparseColumn<T1,SO>, DynamicVector<T2,TF> >
3367 {
3368  typedef typename MultTrait< typename SparseColumn<T1,SO>::ResultType,
3369  DynamicVector<T2,TF> >::Type Type;
3370 };
3371 
3372 template< typename T1, bool TF, typename T2, bool SO >
3373 struct MultTrait< DynamicVector<T1,TF>, SparseColumn<T2,SO> >
3374 {
3375  typedef typename MultTrait< DynamicVector<T1,TF>,
3376  typename SparseColumn<T2,SO>::ResultType >::Type Type;
3377 };
3378 
3379 template< typename T1, bool SO1, typename T2, bool SO2 >
3380 struct MultTrait< SparseColumn<T1,SO1>, DenseColumn<T2,SO2> >
3381 {
3382  typedef typename MultTrait< typename SparseColumn<T1,SO1>::ResultType,
3383  typename DenseColumn <T2,SO2>::ResultType >::Type Type;
3384 };
3385 
3386 template< typename T1, bool SO1, typename T2, bool SO2 >
3387 struct MultTrait< DenseColumn<T1,SO1>, SparseColumn<T2,SO2> >
3388 {
3389  typedef typename MultTrait< typename DenseColumn <T1,SO1>::ResultType,
3390  typename SparseColumn<T2,SO2>::ResultType >::Type Type;
3391 };
3392 
3393 template< typename T1, bool SO, typename T2, bool TF >
3394 struct MultTrait< SparseColumn<T1,SO>, CompressedVector<T2,TF> >
3395 {
3396  typedef typename MultTrait< typename SparseColumn<T1,SO>::ResultType,
3397  CompressedVector<T2,TF> >::Type Type;
3398 };
3399 
3400 template< typename T1, bool TF, typename T2, bool SO >
3401 struct MultTrait< CompressedVector<T1,TF>, SparseColumn<T2,SO> >
3402 {
3403  typedef typename MultTrait< CompressedVector<T1,TF>,
3404  typename SparseColumn<T2,SO>::ResultType >::Type Type;
3405 };
3406 
3407 template< typename T1, bool SO1, typename T2, bool SO2 >
3408 struct MultTrait< SparseColumn<T1,SO1>, SparseColumn<T2,SO2> >
3409 {
3410  typedef typename MultTrait< typename SparseColumn<T1,SO1>::ResultType,
3411  typename SparseColumn<T2,SO2>::ResultType >::Type Type;
3412 };
3413 
3414 template< typename T1, size_t M, size_t N, bool SO1, typename T2, bool SO2 >
3415 struct MultTrait< StaticMatrix<T1,M,N,SO1>, SparseColumn<T2,SO2> >
3416 {
3417  typedef typename MultTrait< StaticMatrix<T1,M,N,SO1>,
3418  typename SparseColumn<T2,SO2>::ResultType >::Type Type;
3419 };
3420 
3421 template< typename T1, bool SO1, typename T2, bool SO2 >
3422 struct MultTrait< DynamicMatrix<T1,SO1>, SparseColumn<T2,SO2> >
3423 {
3424  typedef typename MultTrait< DynamicMatrix<T1,SO1>,
3425  typename SparseColumn<T2,SO2>::ResultType >::Type Type;
3426 };
3427 
3428 template< typename T1, bool SO1, typename T2, bool SO2 >
3429 struct MultTrait< CompressedMatrix<T1,SO1>, SparseColumn<T2,SO2> >
3430 {
3431  typedef typename MultTrait< CompressedMatrix<T1,SO1>,
3432  typename SparseColumn<T2,SO2>::ResultType >::Type Type;
3433 };
3435 //*************************************************************************************************
3436 
3437 
3438 
3439 
3440 //=================================================================================================
3441 //
3442 // DIVTRAIT SPECIALIZATIONS
3443 //
3444 //=================================================================================================
3445 
3446 //*************************************************************************************************
3448 template< typename T1, bool SO, typename T2 >
3449 struct DivTrait< SparseColumn<T1,SO>, T2 >
3450 {
3451  typedef typename DivTrait< typename SparseColumn<T1,SO>::ResultType, T2 >::Type Type;
3453 };
3455 //*************************************************************************************************
3456 
3457 } // namespace blaze
3458 
3459 #endif