diff --git a/Documentation/Examples/Algorithms/Segments/CMakeLists.txt b/Documentation/Examples/Algorithms/Segments/CMakeLists.txt index 7479762c320bf98ac16064ef79b29e814b1f0bfa..dcc32305e8143f3229ebe19021a413f18ce1849e 100644 --- a/Documentation/Examples/Algorithms/Segments/CMakeLists.txt +++ b/Documentation/Examples/Algorithms/Segments/CMakeLists.txt @@ -5,6 +5,7 @@ set( COMMON_EXAMPLES SegmentsExample_CSR_getSerializationType SegmentsExample_CSR_getSegmentsType SegmentsExample_CSR_setSegmentsSizes + SegmentsExample_CSR_getSegmentView ) if( BUILD_CUDA ) diff --git a/Documentation/Examples/Algorithms/Segments/SegmentsExample_CSR_getSegmentView.cpp b/Documentation/Examples/Algorithms/Segments/SegmentsExample_CSR_getSegmentView.cpp new file mode 100644 index 0000000000000000000000000000000000000000..e9ef92da5e0965d45848f3d92746b81f0ac0d21d --- /dev/null +++ b/Documentation/Examples/Algorithms/Segments/SegmentsExample_CSR_getSegmentView.cpp @@ -0,0 +1,47 @@ +#include <iostream> +#include <functional> +#include <TNL/Containers/Vector.h> +#include <TNL/Algorithms/Segments/CSR.h> +#include <TNL/Algorithms/SequentialFor.h> +#include <TNL/Devices/Host.h> +#include <TNL/Devices/Cuda.h> + +template< typename Device > +void SegmentsExample() +{ + using SegmentsType = typename TNL::Algorithms::Segments::CSR< Device, int >; + using SegmentView = typename SegmentsType::SegmentViewType; + + /*** + * Create segments with given segments sizes. + */ + const int size( 5 ); + SegmentsType segments{ 1, 2, 3, 4, 5 }; + auto view = segments.getView(); + + /*** + * Print the elemets mapping using segment view. + */ + std::cout << "Mapping of local indexes to global indexes:" << std::endl; + + auto f = [=] __cuda_callable__ ( int segmentIdx ) { + printf( "Segment idx. %d: ", segmentIdx ); // printf works even in GPU kernels + auto segment = view.getSegmentView( segmentIdx ); + for( auto element : segment ) + printf( "%d -> %d \t", element.localIndex(), element.globalIndex() ); + printf( "\n" ); + }; + TNL::Algorithms::SequentialFor< Device >::exec( 0, size, f ); +} + +int main( int argc, char* argv[] ) +{ + std::cout << "Example of CSR segments on host: " << std::endl; + SegmentsExample< TNL::Devices::Host >(); + +#ifdef HAVE_CUDA + std::cout << "Example of CSR segments on CUDA GPU: " << std::endl; + SegmentsExample< TNL::Devices::Cuda >(); +#endif + return EXIT_SUCCESS; +} diff --git a/Documentation/Examples/Algorithms/Segments/SegmentsExample_CSR_getSegmentView.cu b/Documentation/Examples/Algorithms/Segments/SegmentsExample_CSR_getSegmentView.cu new file mode 120000 index 0000000000000000000000000000000000000000..fd9d2382214c293e70080914e07450ec6d3b86c6 --- /dev/null +++ b/Documentation/Examples/Algorithms/Segments/SegmentsExample_CSR_getSegmentView.cu @@ -0,0 +1 @@ +SegmentsExample_CSR_getSegmentView.cpp \ No newline at end of file diff --git a/Documentation/Examples/Algorithms/Segments/SegmentsExample_CSR_getSegmentsType.cu b/Documentation/Examples/Algorithms/Segments/SegmentsExample_CSR_getSegmentsType.cu new file mode 120000 index 0000000000000000000000000000000000000000..fcb8d7eb740337eb6ddede8c7cb8eff123d17765 --- /dev/null +++ b/Documentation/Examples/Algorithms/Segments/SegmentsExample_CSR_getSegmentsType.cu @@ -0,0 +1 @@ +SegmentsExample_CSR_getSegmentsType.cpp \ No newline at end of file diff --git a/Documentation/Examples/Algorithms/Segments/SegmentsExample_CSR_sequentialForAllSegments.cpp b/Documentation/Examples/Algorithms/Segments/SegmentsExample_CSR_sequentialForAllSegments.cpp new file mode 100644 index 0000000000000000000000000000000000000000..433ae6a61567b3666a888a7559124502a5711334 --- /dev/null +++ b/Documentation/Examples/Algorithms/Segments/SegmentsExample_CSR_sequentialForAllSegments.cpp @@ -0,0 +1,42 @@ +#include <iostream> +#include <functional> +#include <TNL/Containers/Vector.h> +#include <TNL/Algorithms/Segments/CSR.h> +#include <TNL/Devices/Host.h> +#include <TNL/Devices/Cuda.h> + +template< typename Device > +void SegmentsExample() +{ + using SegmentsType = typename TNL::Algorithms::Segments::CSR< Device, int >; + using SegmentViewType = typename SegmentsType::SegmentView; + + /*** + * Create segments with given segments sizes. + */ + SegmentsType segments{ 1, 2, 3, 4, 5 }; + std::cout << "Segments sizes are: " << segments << std::endl; + + /*** + * Print the elemets mapping using segment view. + */ + std::cout << "Elements mapping:" << std::endl; + segments.sequentialForAllSegments( [] __cuda_callable__ ( const SegmentView segment ) { + printf( "Segment idx. %d: \n", segments.getSegmentIndex() ); // printf works even in GPU kernels + for( auto element : segment ) + printf( "%d -> %d ", element.localIndex(), element.globalIndex() ); + } ); + +} + +int main( int argc, char* argv[] ) +{ + std::cout << "Example of CSR segments on host: " << std::endl; + SegmentsExample< TNL::Devices::Host >(); + +#ifdef HAVE_CUDA + std::cout << "Example of CSR segments on CUDA GPU: " << std::endl; + SegmentsExample< TNL::Devices::Cuda >(); +#endif + return EXIT_SUCCESS; +} diff --git a/src/TNL/Algorithms/Segments/CSR.h b/src/TNL/Algorithms/Segments/CSR.h index 5290ac9f4908968c9b2f212bd65262845a8c14d4..4fe24934f21b822f8f8bf26a12ec257bfb15ec4f 100644 --- a/src/TNL/Algorithms/Segments/CSR.h +++ b/src/TNL/Algorithms/Segments/CSR.h @@ -270,12 +270,27 @@ class CSR * * \param segmentIdx is index of the request segment. * \return segment view of given segment. + * + * \par Example + * \include Algorithms/Segments/SegmentsExample_CSR_getSegmentView.cpp + * \par Output + * \include SegmentsExample_CSR_getSegmentView.out */ __cuda_callable__ SegmentViewType getSegmentView( const IndexType segmentIdx ) const; + /** + * \brief Returns reference on constant vector with row offsets used in the CSR format. + * + * \return reference on constant vector with row offsets used in the CSR format. + */ const OffsetsContainer& getOffsets() const; + /** + * \brief Returns reference on vector with row offsets used in the CSR format. + * + * \return reference on vector with row offsets used in the CSR format. + */ OffsetsContainer& getOffsets(); /*** @@ -296,6 +311,13 @@ class CSR template< typename Function > void forAllSegments( Function&& f ) const; + template< typename Function > + void sequentialForSegments( IndexType begin, IndexType end, Function&& f ) const; + + template< typename Function > + void sequentialForAllSegments( Function&& f ) const; + + /*** * \brief Go over all segments and perform a reduction in each of them. */ diff --git a/src/TNL/Algorithms/Segments/CSR.hpp b/src/TNL/Algorithms/Segments/CSR.hpp index ce91e7dc5d01e4336a1f2138173c7d16d354b103..b427f4acdee48540e9a725e1ac157d4a2c8bf26a 100644 --- a/src/TNL/Algorithms/Segments/CSR.hpp +++ b/src/TNL/Algorithms/Segments/CSR.hpp @@ -283,6 +283,30 @@ forAllSegments( Function&& f ) const this->getConstView().forAllSegments( f ); } +template< typename Device, + typename Index, + typename Kernel, + typename IndexAllocator > + template< typename Function > +void +CSR< Device, Index, Kernel, IndexAllocator >:: +sequentialForSegments( IndexType begin, IndexType end, Function&& f ) const +{ + this->getConstView().sequentialForSegments( begin, end, f ); +} + +template< typename Device, + typename Index, + typename Kernel, + typename IndexAllocator > + template< typename Function > +void +CSR< Device, Index, Kernel, IndexAllocator >:: +sequentialForAllSegments( Function&& f ) const +{ + this->getConstView().sequentialForAllSegments( f ); +} + template< typename Device, typename Index, typename Kernel, diff --git a/src/TNL/Algorithms/Segments/CSRView.h b/src/TNL/Algorithms/Segments/CSRView.h index 2d550aada4909390c68ad8c76e7efa5840019f12..5daa3e7c288290d4b17289bcc5a3b24354fe5329 100644 --- a/src/TNL/Algorithms/Segments/CSRView.h +++ b/src/TNL/Algorithms/Segments/CSRView.h @@ -118,6 +118,12 @@ class CSRView template< typename Function > void forAllSegments( Function&& f ) const; + template< typename Function > + void sequentialForSegments( IndexType begin, IndexType end, Function&& f ) const; + + template< typename Function > + void sequentialForAllSegments( Function&& f ) const; + /*** * \brief Go over all segments and perform a reduction in each of them. */ diff --git a/src/TNL/Algorithms/Segments/CSRView.hpp b/src/TNL/Algorithms/Segments/CSRView.hpp index f4cfc2c786e37c9d73ecd617d6c1d3591f7a5600..7de19383738a0dcbfec720f8336b1bbc6ed50123 100644 --- a/src/TNL/Algorithms/Segments/CSRView.hpp +++ b/src/TNL/Algorithms/Segments/CSRView.hpp @@ -238,6 +238,29 @@ forAllSegments( Function&& f ) const this->forSegments( 0, this->getSegmentsCount(), f ); } +template< typename Device, + typename Index, + typename Kernel > + template< typename Function > +void +CSRView< Device, Index, Kernel >:: +sequentialForSegments( IndexType begin, IndexType end, Function&& function ) const +{ + for( IndexType i = begin; i < end; i++ ) + forSegments( i, i + 1, function ); +} + +template< typename Device, + typename Index, + typename Kernel > + template< typename Function > +void +CSRView< Device, Index, Kernel >:: +sequentialForAllSegments( Function&& f ) const +{ + this->sequentialForSegments( 0, this->getSegmentsCount(), f ); +} + template< typename Device, typename Index, typename Kernel >