Cabana 0.8.0-dev
 
Loading...
Searching...
No Matches
Cabana_Grid_IndexSpace.hpp
Go to the documentation of this file.
1/****************************************************************************
2 * Copyright (c) 2018-2023 by the Cabana authors *
3 * All rights reserved. *
4 * *
5 * This file is part of the Cabana library. Cabana is distributed under a *
6 * BSD 3-clause license. For the licensing terms see the LICENSE file in *
7 * the top-level directory. *
8 * *
9 * SPDX-License-Identifier: BSD-3-Clause *
10 ****************************************************************************/
11
16#ifndef CABANA_GRID_INDEXSPACE_HPP
17#define CABANA_GRID_INDEXSPACE_HPP
18
19#include <Cabana_Utils.hpp> // FIXME: remove after next release.
20
21#include <Kokkos_Core.hpp>
22
23#include <algorithm>
24#include <array>
25#include <string>
26
27namespace Cabana
28{
29namespace Grid
30{
31//---------------------------------------------------------------------------//
35template <long N>
37{
38 public:
40 static constexpr long Rank = N;
41
44 {
45 std::fill( _min.data(), _min.data() + Rank, -1 );
46 std::fill( _max.data(), _max.data() + Rank, -1 );
47 }
48
52 template <typename Scalar>
53 IndexSpace( const std::initializer_list<Scalar>& size )
54 {
55 std::fill( _min.data(), _min.data() + Rank, 0 );
56 std::copy( size.begin(), size.end(), _max.data() );
57 }
58
62 template <typename Scalar>
63 IndexSpace( const std::initializer_list<Scalar>& min,
64 const std::initializer_list<Scalar>& max )
65 {
66 std::copy( min.begin(), min.end(), _min.data() );
67 std::copy( max.begin(), max.end(), _max.data() );
68 }
69
73 IndexSpace( const std::array<long, N>& size )
74 {
75 std::fill( _min.data(), _min.data() + Rank, 0 );
76 std::copy( size.begin(), size.end(), _max.data() );
77 }
78
82 IndexSpace( const std::array<long, N>& min, const std::array<long, N>& max )
83 {
84 std::copy( min.begin(), min.end(), _min.data() );
85 std::copy( max.begin(), max.end(), _max.data() );
86 }
87
89 KOKKOS_INLINE_FUNCTION
90 bool operator==( const IndexSpace<N>& rhs ) const
91 {
92 for ( long i = 0; i < N; ++i )
93 {
94 if ( min( i ) != rhs.min( i ) || max( i ) != rhs.max( i ) )
95 return false;
96 }
97 return true;
98 }
99
101 KOKKOS_INLINE_FUNCTION
102 bool operator!=( const IndexSpace<N>& rhs ) const
103 {
104 return !( operator==( rhs ) );
105 }
106
108 KOKKOS_INLINE_FUNCTION
109 long min( const long dim ) const { return _min[dim]; }
110
112 KOKKOS_INLINE_FUNCTION
113 Kokkos::Array<long, Rank> min() const { return _min; }
114
116 KOKKOS_INLINE_FUNCTION
117 long max( const long dim ) const { return _max[dim]; }
118
120 KOKKOS_INLINE_FUNCTION
121 Kokkos::Array<long, Rank> max() const { return _max; }
122
124 KOKKOS_INLINE_FUNCTION
125 Kokkos::pair<long, long> range( const long dim ) const
126 {
127 return Kokkos::tie( _min[dim], _max[dim] );
128 }
129
131 KOKKOS_INLINE_FUNCTION
132 long rank() const { return Rank; }
133
135 KOKKOS_INLINE_FUNCTION
136 long extent( const long dim ) const { return _max[dim] - _min[dim]; }
137
139 KOKKOS_INLINE_FUNCTION
140 long size() const
141 {
142 long size = 1;
143 for ( long d = 0; d < Rank; ++d )
144 size *= extent( d );
145 return size;
146 }
147
149 KOKKOS_INLINE_FUNCTION
150 bool inRange( const long index[N] ) const
151 {
152 bool result = true;
153 for ( long i = 0; i < N; ++i )
154 result =
155 result && ( _min[i] <= index[i] ) && ( index[i] < _max[i] );
156 return result;
157 }
158
159 protected:
161 Kokkos::Array<long, Rank> _min;
162
164 Kokkos::Array<long, Rank> _max;
165};
166
167//---------------------------------------------------------------------------//
173template <class ExecutionSpace>
174Kokkos::RangePolicy<ExecutionSpace>
175createExecutionPolicy( const IndexSpace<1>& index_space, const ExecutionSpace& )
176{
177 return Kokkos::RangePolicy<ExecutionSpace>( index_space.min( 0 ),
178 index_space.max( 0 ) );
179}
180
181//---------------------------------------------------------------------------//
188template <class ExecutionSpace, class WorkTag>
189Kokkos::RangePolicy<ExecutionSpace, WorkTag>
190createExecutionPolicy( const IndexSpace<1>& index_space, const ExecutionSpace&,
191 const WorkTag& )
192{
193 return Kokkos::RangePolicy<ExecutionSpace, WorkTag>( index_space.min( 0 ),
194 index_space.max( 0 ) );
195}
196
197//---------------------------------------------------------------------------//
202template <class IndexSpace_t, class ExecutionSpace>
203Kokkos::MDRangePolicy<ExecutionSpace, Kokkos::Rank<IndexSpace_t::Rank>>
204createExecutionPolicy( const IndexSpace_t& index_space, const ExecutionSpace& )
205{
206 return Kokkos::MDRangePolicy<ExecutionSpace,
207 Kokkos::Rank<IndexSpace_t::Rank>>(
208 index_space.min(), index_space.max() );
209}
210
211//---------------------------------------------------------------------------//
217template <class IndexSpace_t, class ExecutionSpace, class WorkTag>
218Kokkos::MDRangePolicy<ExecutionSpace, WorkTag, Kokkos::Rank<IndexSpace_t::Rank>>
219createExecutionPolicy( const IndexSpace_t& index_space, const ExecutionSpace&,
220 const WorkTag& )
221{
222 return Kokkos::MDRangePolicy<ExecutionSpace, WorkTag,
223 Kokkos::Rank<IndexSpace_t::Rank>>(
224 index_space.min(), index_space.max() );
225}
226
227//---------------------------------------------------------------------------//
234template <class Scalar, class... Params>
235Kokkos::View<Scalar*, Params...> createView( const std::string& label,
236 const IndexSpace<1>& index_space )
237{
238 return Kokkos::View<Scalar*, Params...>(
239 Kokkos::ViewAllocateWithoutInitializing( label ),
240 index_space.extent( 0 ) );
241}
242
243//---------------------------------------------------------------------------//
251template <class Scalar, class... Params>
252Kokkos::View<Scalar*, Params..., Kokkos::MemoryUnmanaged>
253createView( const IndexSpace<1>& index_space, Scalar* data )
254{
255 return Kokkos::View<Scalar*, Params..., Kokkos::MemoryUnmanaged>(
256 data, index_space.extent( 0 ) );
257}
258
259//---------------------------------------------------------------------------//
267template <class Scalar, class... Params>
268Kokkos::View<Scalar**, Params...> createView( const std::string& label,
269 const IndexSpace<2>& index_space )
270{
271 return Kokkos::View<Scalar**, Params...>(
272 Kokkos::ViewAllocateWithoutInitializing( label ),
273 index_space.extent( 0 ), index_space.extent( 1 ) );
274}
275
276//---------------------------------------------------------------------------//
284template <class Scalar, class... Params>
285Kokkos::View<Scalar**, Params..., Kokkos::MemoryUnmanaged>
286createView( const IndexSpace<2>& index_space, Scalar* data )
287{
288 return Kokkos::View<Scalar**, Params..., Kokkos::MemoryUnmanaged>(
289 data, index_space.extent( 0 ), index_space.extent( 1 ) );
290}
291
292//---------------------------------------------------------------------------//
300template <class Scalar, class... Params>
301Kokkos::View<Scalar***, Params...>
302createView( const std::string& label, const IndexSpace<3>& index_space )
303{
304 return Kokkos::View<Scalar***, Params...>(
305 Kokkos::ViewAllocateWithoutInitializing( label ),
306 index_space.extent( 0 ), index_space.extent( 1 ),
307 index_space.extent( 2 ) );
308}
309
310//---------------------------------------------------------------------------//
318template <class Scalar, class... Params>
319Kokkos::View<Scalar***, Params..., Kokkos::MemoryUnmanaged>
320createView( const IndexSpace<3>& index_space, Scalar* data )
321{
322 return Kokkos::View<Scalar***, Params..., Kokkos::MemoryUnmanaged>(
323 data, index_space.extent( 0 ), index_space.extent( 1 ),
324 index_space.extent( 2 ) );
325}
326
327//---------------------------------------------------------------------------//
334template <class Scalar, class... Params>
335Kokkos::View<Scalar****, Params...>
336createView( const std::string& label, const IndexSpace<4>& index_space )
337{
338 return Kokkos::View<Scalar****, Params...>(
339 Kokkos::ViewAllocateWithoutInitializing( label ),
340 index_space.extent( 0 ), index_space.extent( 1 ),
341 index_space.extent( 2 ), index_space.extent( 3 ) );
342}
343
344//---------------------------------------------------------------------------//
352template <class Scalar, class... Params>
353Kokkos::View<Scalar****, Params..., Kokkos::MemoryUnmanaged>
354createView( const IndexSpace<4>& index_space, Scalar* data )
355{
356 return Kokkos::View<Scalar****, Params..., Kokkos::MemoryUnmanaged>(
357 data, index_space.extent( 0 ), index_space.extent( 1 ),
358 index_space.extent( 2 ), index_space.extent( 3 ) );
359}
360
361//---------------------------------------------------------------------------//
368template <class ViewType>
369KOKKOS_INLINE_FUNCTION auto createSubview( const ViewType& view,
370 const IndexSpace<1>& index_space )
371 -> decltype( Kokkos::subview( view, index_space.range( 0 ) ) )
372{
373 static_assert( 1 == ViewType::rank, "Incorrect view rank" );
374 return Kokkos::subview( view, index_space.range( 0 ) );
375}
376
377//---------------------------------------------------------------------------//
384template <class ViewType>
385KOKKOS_INLINE_FUNCTION auto createSubview( const ViewType& view,
386 const IndexSpace<2>& index_space )
387 -> decltype( Kokkos::subview( view, index_space.range( 0 ),
388 index_space.range( 1 ) ) )
389{
390 static_assert( 2 == ViewType::rank, "Incorrect view rank" );
391 return Kokkos::subview( view, index_space.range( 0 ),
392 index_space.range( 1 ) );
393}
394
395//---------------------------------------------------------------------------//
402template <class ViewType>
403KOKKOS_INLINE_FUNCTION auto createSubview( const ViewType& view,
404 const IndexSpace<3>& index_space )
405 -> decltype( Kokkos::subview( view, index_space.range( 0 ),
406 index_space.range( 1 ),
407 index_space.range( 2 ) ) )
408{
409 static_assert( 3 == ViewType::rank, "Incorrect view rank" );
410 return Kokkos::subview( view, index_space.range( 0 ),
411 index_space.range( 1 ), index_space.range( 2 ) );
412}
413
414//---------------------------------------------------------------------------//
421template <class ViewType>
422KOKKOS_INLINE_FUNCTION auto createSubview( const ViewType& view,
423 const IndexSpace<4>& index_space )
424 -> decltype( Kokkos::subview( view, index_space.range( 0 ),
425 index_space.range( 1 ),
426 index_space.range( 2 ),
427 index_space.range( 3 ) ) )
428{
429 static_assert( 4 == ViewType::rank, "Incorrect view rank" );
430 return Kokkos::subview( view, index_space.range( 0 ),
431 index_space.range( 1 ), index_space.range( 2 ),
432 index_space.range( 3 ) );
433}
434
435//---------------------------------------------------------------------------//
441template <long N>
443 const long size )
444{
445 std::array<long, N + 1> min;
446 for ( int d = 0; d < N; ++d )
447 min[d] = index_space.min( d );
448 min[N] = 0;
449
450 std::array<long, N + 1> max;
451 for ( int d = 0; d < N; ++d )
452 max[d] = index_space.max( d );
453 max[N] = size;
454
455 return IndexSpace<N + 1>( min, max );
456}
457
458//---------------------------------------------------------------------------//
464template <long N>
466 const long min, const long max )
467{
468 std::array<long, N + 1> range_min;
469 for ( int d = 0; d < N; ++d )
470 range_min[d] = index_space.min( d );
471 range_min[N] = min;
472
473 std::array<long, N + 1> range_max;
474 for ( int d = 0; d < N; ++d )
475 range_max[d] = index_space.max( d );
476 range_max[N] = max;
477
478 return IndexSpace<N + 1>( range_min, range_max );
479}
480
481//---------------------------------------------------------------------------//
482
483} // namespace Grid
484} // namespace Cabana
485
486#endif // end CABANA_GRID_INDEXSPACE_HPP
KOKKOS_INLINE_FUNCTION auto createSubview(const ViewType &view, const IndexSpace< 1 > &index_space) -> decltype(Kokkos::subview(view, index_space.range(0)))
Given a view create a subview over the given index space.
Definition Cabana_Grid_IndexSpace.hpp:369
Kokkos::RangePolicy< ExecutionSpace > createExecutionPolicy(const IndexSpace< 1 > &index_space, const ExecutionSpace &)
Create a multi-dimensional execution policy over an index space.
Definition Cabana_Grid_IndexSpace.hpp:175
Kokkos::View< Scalar *, Params... > createView(const std::string &label, const IndexSpace< 1 > &index_space)
Given an index space create a view over the extent of that index space.
Definition Cabana_Grid_IndexSpace.hpp:235
IndexSpace< N+1 > appendDimension(const IndexSpace< N > &index_space, const long size)
Given an N-dimensional index space append an additional dimension with the given size.
Definition Cabana_Grid_IndexSpace.hpp:442
Cabana utilities.
Structured index space.
Definition Cabana_Grid_IndexSpace.hpp:37
KOKKOS_INLINE_FUNCTION bool inRange(const long index[N]) const
Determine if a set of indices is within the range of the index space.
Definition Cabana_Grid_IndexSpace.hpp:150
KOKKOS_INLINE_FUNCTION Kokkos::Array< long, Rank > max() const
Get the maximum indices in all dimensions.
Definition Cabana_Grid_IndexSpace.hpp:121
KOKKOS_INLINE_FUNCTION Kokkos::Array< long, Rank > min() const
Get the minimum indices in all dimensions.
Definition Cabana_Grid_IndexSpace.hpp:113
Kokkos::Array< long, Rank > _max
Maximum index bounds.
Definition Cabana_Grid_IndexSpace.hpp:164
IndexSpace(const std::array< long, N > &min, const std::array< long, N > &max)
Vector range constructor.
Definition Cabana_Grid_IndexSpace.hpp:82
KOKKOS_INLINE_FUNCTION long max(const long dim) const
Get the maximum index in a given dimension.
Definition Cabana_Grid_IndexSpace.hpp:117
KOKKOS_INLINE_FUNCTION long min(const long dim) const
Get the minimum index in a given dimension.
Definition Cabana_Grid_IndexSpace.hpp:109
KOKKOS_INLINE_FUNCTION bool operator==(const IndexSpace< N > &rhs) const
Comparison operator.
Definition Cabana_Grid_IndexSpace.hpp:90
static constexpr long Rank
Number of dimensions.
Definition Cabana_Grid_IndexSpace.hpp:40
KOKKOS_INLINE_FUNCTION Kokkos::pair< long, long > range(const long dim) const
Get the range of a given dimension.
Definition Cabana_Grid_IndexSpace.hpp:125
Kokkos::Array< long, Rank > _min
Minimum index bounds.
Definition Cabana_Grid_IndexSpace.hpp:161
KOKKOS_INLINE_FUNCTION bool operator!=(const IndexSpace< N > &rhs) const
Comparison operator.
Definition Cabana_Grid_IndexSpace.hpp:102
KOKKOS_INLINE_FUNCTION long size() const
Get the total size of the index space.
Definition Cabana_Grid_IndexSpace.hpp:140
KOKKOS_INLINE_FUNCTION long rank() const
Get the number of dimensions.
Definition Cabana_Grid_IndexSpace.hpp:132
KOKKOS_INLINE_FUNCTION long extent(const long dim) const
Get the extent of a given dimension.
Definition Cabana_Grid_IndexSpace.hpp:136
IndexSpace(const std::initializer_list< Scalar > &min, const std::initializer_list< Scalar > &max)
Initializer list range constructor.
Definition Cabana_Grid_IndexSpace.hpp:63
IndexSpace()
Default constructor.
Definition Cabana_Grid_IndexSpace.hpp:43
IndexSpace(const std::initializer_list< Scalar > &size)
Initializer list size constructor.
Definition Cabana_Grid_IndexSpace.hpp:53
IndexSpace(const std::array< long, N > &size)
Vector size constructor.
Definition Cabana_Grid_IndexSpace.hpp:73
Core: particle data structures and algorithms.
Definition Cabana_AoSoA.hpp:36
auto size(SliceType slice, typename std::enable_if< is_slice< SliceType >::value, int >::type *=0)
Check slice size (differs from Kokkos View).
Definition Cabana_Slice.hpp:1012