From e0b5dfaf5e93e0fea9fe3882e2e4f7114300de49 Mon Sep 17 00:00:00 2001 From: Lukas Cejka <lukas.ostatek@gmail.com> Date: Fri, 30 Nov 2018 08:45:16 +0100 Subject: [PATCH] Added getNonZeroRowLength for backup purposes. --- src/TNL/Matrices/CSR.h | 2 + src/TNL/Matrices/CSR_impl.h | 9 + src/TNL/Matrices/ChunkedEllpack.h | 2 + src/TNL/Matrices/ChunkedEllpack_impl.h | 17 +- src/TNL/Matrices/Ellpack.h | 2 + src/TNL/Matrices/Ellpack_impl.h | 9 + src/TNL/Matrices/SlicedEllpack.h | 2 + src/TNL/Matrices/SlicedEllpack_impl.h | 10 ++ src/TNL/Matrices/SparseRow.h | 3 + src/TNL/Matrices/SparseRow_impl.h | 27 +++ .../Matrices/SparseMatrixTest_impl.h | 162 +++++++++++------- 11 files changed, 181 insertions(+), 64 deletions(-) diff --git a/src/TNL/Matrices/CSR.h b/src/TNL/Matrices/CSR.h index ef7ba5d6f9..1ce7d330bb 100644 --- a/src/TNL/Matrices/CSR.h +++ b/src/TNL/Matrices/CSR.h @@ -75,6 +75,8 @@ public: __cuda_callable__ IndexType getRowLengthFast( const IndexType row ) const; + + IndexType getNonZeroRowLength( const IndexType row ) const; template< typename Real2, typename Device2, typename Index2 > void setLike( const CSR< Real2, Device2, Index2 >& matrix ); diff --git a/src/TNL/Matrices/CSR_impl.h b/src/TNL/Matrices/CSR_impl.h index b4dff85470..5849bbaa76 100644 --- a/src/TNL/Matrices/CSR_impl.h +++ b/src/TNL/Matrices/CSR_impl.h @@ -131,6 +131,15 @@ Index CSR< Real, Device, Index >::getRowLengthFast( const IndexType row ) const return this->rowPointers[ row + 1 ] - this->rowPointers[ row ]; } +template< typename Real, + typename Device, + typename Index > +Index CSR< Real, Device, Index >::getNonZeroRowLength( const IndexType row ) const +{ + ConstMatrixRow matrixRow = getRow( row ); + return matrixRow.getNonZeroElementsCount(); +} + template< typename Real, typename Device, typename Index > diff --git a/src/TNL/Matrices/ChunkedEllpack.h b/src/TNL/Matrices/ChunkedEllpack.h index 35bbfa8979..ff889a49fe 100644 --- a/src/TNL/Matrices/ChunkedEllpack.h +++ b/src/TNL/Matrices/ChunkedEllpack.h @@ -104,6 +104,8 @@ public: __cuda_callable__ IndexType getRowLengthFast( const IndexType row ) const; + + IndexType getNonZeroRowLength( const IndexType row ) const; template< typename Real2, typename Device2, typename Index2 > void setLike( const ChunkedEllpack< Real2, Device2, Index2 >& matrix ); diff --git a/src/TNL/Matrices/ChunkedEllpack_impl.h b/src/TNL/Matrices/ChunkedEllpack_impl.h index 00cee63bb2..56a5114912 100644 --- a/src/TNL/Matrices/ChunkedEllpack_impl.h +++ b/src/TNL/Matrices/ChunkedEllpack_impl.h @@ -308,6 +308,15 @@ Index ChunkedEllpack< Real, Device, Index >::getRowLengthFast( const IndexType r return rowPointers[ row + 1 ] - rowPointers[ row ]; } +template< typename Real, + typename Device, + typename Index > +Index ChunkedEllpack< Real, Device, Index >::getNonZeroRowLength( const IndexType row ) const +{ + ConstMatrixRow matrixRow = getRow( row ); + return matrixRow.getNonZeroElementsCount(); +} + template< typename Real, typename Device, typename Index > @@ -979,10 +988,10 @@ getRow( const IndexType rowIndex ) const { const IndexType rowOffset = this->rowPointers[ rowIndex ]; const IndexType rowLength = this->rowPointers[ rowIndex + 1 ] - rowOffset; - return MatrixRow( &this->columnIndexes[ rowOffset ], - &this->values[ rowOffset ], - rowLength, - 1 ); + return ConstMatrixRow( &this->columnIndexes[ rowOffset ], + &this->values[ rowOffset ], + rowLength, + 1 ); } diff --git a/src/TNL/Matrices/Ellpack.h b/src/TNL/Matrices/Ellpack.h index 1646db1c5c..7d17ff07e8 100644 --- a/src/TNL/Matrices/Ellpack.h +++ b/src/TNL/Matrices/Ellpack.h @@ -67,6 +67,8 @@ public: __cuda_callable__ IndexType getRowLengthFast( const IndexType row ) const; + + IndexType getNonZeroRowLength( const IndexType row ) const; template< typename Real2, typename Device2, typename Index2 > void setLike( const Ellpack< Real2, Device2, Index2 >& matrix ); diff --git a/src/TNL/Matrices/Ellpack_impl.h b/src/TNL/Matrices/Ellpack_impl.h index 6186206439..bf3063cd60 100644 --- a/src/TNL/Matrices/Ellpack_impl.h +++ b/src/TNL/Matrices/Ellpack_impl.h @@ -123,6 +123,15 @@ Index Ellpack< Real, Device, Index >::getRowLengthFast( const IndexType row ) co return this->rowLengths; } +template< typename Real, + typename Device, + typename Index > +Index Ellpack< Real, Device, Index >::getNonZeroRowLength( const IndexType row ) const +{ + ConstMatrixRow matrixRow = getRow( row ); + return matrixRow.getNonZeroElementsCount(); +} + template< typename Real, typename Device, typename Index > diff --git a/src/TNL/Matrices/SlicedEllpack.h b/src/TNL/Matrices/SlicedEllpack.h index 6f68f2fa8a..0fc9ccb0b2 100644 --- a/src/TNL/Matrices/SlicedEllpack.h +++ b/src/TNL/Matrices/SlicedEllpack.h @@ -95,6 +95,8 @@ public: __cuda_callable__ IndexType getRowLengthFast( const IndexType row ) const; + + IndexType getNonZeroRowLength( const IndexType row ) const; template< typename Real2, typename Device2, typename Index2 > void setLike( const SlicedEllpack< Real2, Device2, Index2, SliceSize >& matrix ); diff --git a/src/TNL/Matrices/SlicedEllpack_impl.h b/src/TNL/Matrices/SlicedEllpack_impl.h index d186bc0471..59b548ade4 100644 --- a/src/TNL/Matrices/SlicedEllpack_impl.h +++ b/src/TNL/Matrices/SlicedEllpack_impl.h @@ -121,6 +121,16 @@ Index SlicedEllpack< Real, Device, Index, SliceSize >::getRowLengthFast( const I return this->sliceCompressedRowLengths[ slice ]; } +template< typename Real, + typename Device, + typename Index , + int SliceSize > +Index SlicedEllpack< Real, Device, Index, SliceSize >::getNonZeroRowLength( const IndexType row ) const +{ + ConstMatrixRow matrixRow = getRow( row ); + return matrixRow.getNonZeroElementsCount(); +} + template< typename Real, typename Device, typename Index, diff --git a/src/TNL/Matrices/SparseRow.h b/src/TNL/Matrices/SparseRow.h index e7547ee679..4f8efbdb50 100644 --- a/src/TNL/Matrices/SparseRow.h +++ b/src/TNL/Matrices/SparseRow.h @@ -51,6 +51,9 @@ class SparseRow __cuda_callable__ Index getLength() const; + + __cuda_callable__ + Index getNonZeroElementsCount() const; void print( std::ostream& str ) const; diff --git a/src/TNL/Matrices/SparseRow_impl.h b/src/TNL/Matrices/SparseRow_impl.h index f6921b15bb..2f0d87d5eb 100644 --- a/src/TNL/Matrices/SparseRow_impl.h +++ b/src/TNL/Matrices/SparseRow_impl.h @@ -11,6 +11,7 @@ #pragma once #include <TNL/Matrices/SparseRow.h> +#include <TNL/ParallelFor.h> namespace TNL { namespace Matrices { @@ -107,6 +108,32 @@ getLength() const return length; } +template< typename Real, typename Index > +__cuda_callable__ +Index +SparseRow< Real, Index >:: +getNonZeroElementsCount() const +{ + using NonConstIndex = typename std::remove_const< Index >::type; + + NonConstIndex elementCount ( 0 ); + +// auto computeNonzeros = [this, &elementCount] /*__cuda_callable__*/ ( NonConstIndex i ) mutable +// { +// if( getElementValue( i ) != ( Real ) 0 ) +// elementCount++; +// }; + +// ParallelFor< Device >::exec( ( NonConstIndex ) 0, length, computeNonzeros ); +// The ParallelFor::exec() function needs a < DeviceType >, how to get this into SparseRow? + + for( NonConstIndex i = 0; i < length; i++ ) + if( getElementValue( i ) != 0 ) // This returns the same amount of elements in a row as does getRowLength(). WHY? + elementCount++; + + return elementCount; +} + template< typename Real, typename Index > void SparseRow< Real, Index >:: diff --git a/src/UnitTests/Matrices/SparseMatrixTest_impl.h b/src/UnitTests/Matrices/SparseMatrixTest_impl.h index 0c1ccbbdd9..d2dae912e6 100644 --- a/src/UnitTests/Matrices/SparseMatrixTest_impl.h +++ b/src/UnitTests/Matrices/SparseMatrixTest_impl.h @@ -136,66 +136,108 @@ void test_SetCompressedRowLengths() m.setCompressedRowLengths( rowLengths ); - - if( m.getType() == TNL::String( TNL::String( "Matrices::CSR< ") + - TNL::String( TNL::getType< RealType >() ) + - TNL::String( ", " ) + - TNL::String( Matrix::DeviceType::getDeviceType() ) + - TNL::String( ", " ) + - TNL::String( TNL::getType< IndexType >() ) + - TNL::String( " >" ) ) - ) - { - EXPECT_EQ( m.getRowLength( 0 ), 3 ); - EXPECT_EQ( m.getRowLength( 1 ), 3 ); - EXPECT_EQ( m.getRowLength( 2 ), 1 ); - EXPECT_EQ( m.getRowLength( 3 ), 2 ); - EXPECT_EQ( m.getRowLength( 4 ), 3 ); - EXPECT_EQ( m.getRowLength( 5 ), 4 ); - EXPECT_EQ( m.getRowLength( 6 ), 5 ); - EXPECT_EQ( m.getRowLength( 7 ), 6 ); - EXPECT_EQ( m.getRowLength( 8 ), 7 ); - EXPECT_EQ( m.getRowLength( 9 ), 8 ); - } - else if( m.getType() == TNL::String( TNL::String( "Matrices::Ellpack< ") + - TNL::String( TNL::getType< RealType >() ) + - TNL::String( ", " ) + - TNL::String( Matrix::DeviceType::getDeviceType() ) + - TNL::String( ", " ) + - TNL::String( TNL::getType< IndexType >() ) + - TNL::String( " >" ) ) - || - m.getType() == TNL::String( TNL::String( "Matrices::SlicedEllpack< ") + - TNL::String( TNL::getType< RealType >() ) + - TNL::String( ", " ) + - TNL::String( Matrix::DeviceType::getDeviceType() ) + - TNL::String( " >" ) ) - ) - { - EXPECT_EQ( m.getRowLength( 0 ), 8 ); - EXPECT_EQ( m.getRowLength( 1 ), 8 ); - EXPECT_EQ( m.getRowLength( 2 ), 8 ); - EXPECT_EQ( m.getRowLength( 3 ), 8 ); - EXPECT_EQ( m.getRowLength( 4 ), 8 ); - EXPECT_EQ( m.getRowLength( 5 ), 8 ); - EXPECT_EQ( m.getRowLength( 6 ), 8 ); - EXPECT_EQ( m.getRowLength( 7 ), 8 ); - EXPECT_EQ( m.getRowLength( 8 ), 8 ); - EXPECT_EQ( m.getRowLength( 9 ), 8 ); - } - else - { - EXPECT_EQ( m.getRowLength( 0 ), 3 ); - EXPECT_EQ( m.getRowLength( 1 ), 3 ); - EXPECT_EQ( m.getRowLength( 2 ), 1 ); - EXPECT_EQ( m.getRowLength( 3 ), 2 ); - EXPECT_EQ( m.getRowLength( 4 ), 3 ); - EXPECT_EQ( m.getRowLength( 5 ), 4 ); - EXPECT_EQ( m.getRowLength( 6 ), 5 ); - EXPECT_EQ( m.getRowLength( 7 ), 6 ); - EXPECT_EQ( m.getRowLength( 8 ), 7 ); - EXPECT_EQ( m.getRowLength( 9 ), 8 ); - } + RealType realValue = 1; // Do this for every individual row, to assure that non-zero values are not assigned where they're not supposed to be, aka, outside of compressed Row Length + for( IndexType i = 0; i < rows; i++ ) + for( IndexType j = 0; j < cols; j++ ) + m.setElement( i, j, realValue++ ); + + + EXPECT_EQ( m.getNonZeroRowLength( 0 ), 3 ); + EXPECT_EQ( m.getNonZeroRowLength( 1 ), 3 ); + EXPECT_EQ( m.getNonZeroRowLength( 2 ), 1 ); + EXPECT_EQ( m.getNonZeroRowLength( 3 ), 2 ); + EXPECT_EQ( m.getNonZeroRowLength( 4 ), 3 ); + EXPECT_EQ( m.getNonZeroRowLength( 5 ), 4 ); + EXPECT_EQ( m.getNonZeroRowLength( 6 ), 5 ); + EXPECT_EQ( m.getNonZeroRowLength( 7 ), 6 ); + EXPECT_EQ( m.getNonZeroRowLength( 8 ), 7 ); + EXPECT_EQ( m.getNonZeroRowLength( 9 ), 8 ); + +// if( m.getType() == TNL::String( TNL::String( "Matrices::CSR< ") + +// TNL::String( TNL::getType< RealType >() ) + +// TNL::String( ", " ) + +// TNL::String( Matrix::DeviceType::getDeviceType() ) + +// //TNL::String( ", " ) + +// //TNL::String( TNL::getType< IndexType >() ) + +// TNL::String( " >" ) ) +// ) +// { +// EXPECT_EQ( m.getRowLength( 0 ), 3 ); +// EXPECT_EQ( m.getRowLength( 1 ), 3 ); +// EXPECT_EQ( m.getRowLength( 2 ), 1 ); +// EXPECT_EQ( m.getRowLength( 3 ), 2 ); +// EXPECT_EQ( m.getRowLength( 4 ), 3 ); +// EXPECT_EQ( m.getRowLength( 5 ), 4 ); +// EXPECT_EQ( m.getRowLength( 6 ), 5 ); +// EXPECT_EQ( m.getRowLength( 7 ), 6 ); +// EXPECT_EQ( m.getRowLength( 8 ), 7 ); +// EXPECT_EQ( m.getRowLength( 9 ), 8 ); +// } +// else if( m.getType() == TNL::String( TNL::String( "Matrices::AdEllpack< ") + +// TNL::String( TNL::getType< RealType >() ) + +// TNL::String( ", " ) + +// TNL::String( Matrix::DeviceType::getDeviceType() ) + +// TNL::String( ", " ) + +// TNL::String( TNL::getType< IndexType >() ) + +// TNL::String( " >" ) ) +// || +// m.getType() == TNL::String( TNL::String( "Matrices::SlicedEllpack< ") + +// TNL::String( TNL::getType< RealType >() ) + +// TNL::String( ", " ) + +// TNL::String( Matrix::DeviceType::getDeviceType() ) + +// TNL::String( " >" ) ) +// ) +// { +// EXPECT_EQ( m.getRowLength( 0 ), 8 ); +// EXPECT_EQ( m.getRowLength( 1 ), 8 ); +// EXPECT_EQ( m.getRowLength( 2 ), 8 ); +// EXPECT_EQ( m.getRowLength( 3 ), 8 ); +// EXPECT_EQ( m.getRowLength( 4 ), 8 ); +// EXPECT_EQ( m.getRowLength( 5 ), 8 ); +// EXPECT_EQ( m.getRowLength( 6 ), 8 ); +// EXPECT_EQ( m.getRowLength( 7 ), 8 ); +// EXPECT_EQ( m.getRowLength( 8 ), 8 ); +// EXPECT_EQ( m.getRowLength( 9 ), 8 ); +// } +// else if( m.getType() == TNL::String( TNL::String( "Matrices::Ellpack< ") + +// TNL::String( TNL::getType< RealType >() ) + +// TNL::String( ", " ) + +// TNL::String( Matrix::DeviceType::getDeviceType() ) + +// TNL::String( ", " ) + +// TNL::String( TNL::getType< IndexType >() ) + +// TNL::String( " >" ) ) +// || +// m.getType() == TNL::String( TNL::String( "Matrices::ChunkedEllpack< ") + +// TNL::String( TNL::getType< RealType >() ) + +// TNL::String( ", " ) + +// TNL::String( Matrix::DeviceType::getDeviceType() ) + +// TNL::String( " >" ) ) +// ) +// { +// EXPECT_EQ( m.getNonZeroRowLength( 0 ), 3 ); +// EXPECT_EQ( m.getNonZeroRowLength( 1 ), 3 ); +// EXPECT_EQ( m.getNonZeroRowLength( 2 ), 1 ); +// EXPECT_EQ( m.getNonZeroRowLength( 3 ), 2 ); +// EXPECT_EQ( m.getNonZeroRowLength( 4 ), 3 ); +// EXPECT_EQ( m.getNonZeroRowLength( 5 ), 4 ); +// EXPECT_EQ( m.getNonZeroRowLength( 6 ), 5 ); +// EXPECT_EQ( m.getNonZeroRowLength( 7 ), 6 ); +// EXPECT_EQ( m.getNonZeroRowLength( 8 ), 7 ); +// EXPECT_EQ( m.getNonZeroRowLength( 9 ), 8 ); +// } +// else +// { +// EXPECT_EQ( m.getRowLength( 0 ), 3 ); +// EXPECT_EQ( m.getRowLength( 1 ), 3 ); +// EXPECT_EQ( m.getRowLength( 2 ), 1 ); +// EXPECT_EQ( m.getRowLength( 3 ), 2 ); +// EXPECT_EQ( m.getRowLength( 4 ), 3 ); +// EXPECT_EQ( m.getRowLength( 5 ), 4 ); +// EXPECT_EQ( m.getRowLength( 6 ), 5 ); +// EXPECT_EQ( m.getRowLength( 7 ), 6 ); +// EXPECT_EQ( m.getRowLength( 8 ), 7 ); +// EXPECT_EQ( m.getRowLength( 9 ), 8 ); +// } } template< typename Matrix1, typename Matrix2 > -- GitLab