12#include <Kokkos_Assert.hpp>
13#include <Kokkos_Macros.hpp>
15#include "detail/type_seq.hpp"
17#include "discrete_element.hpp"
18#include "discrete_vector.hpp"
25template <
class... DDims>
33template <
class... Tags>
44template <
class... Tags>
47 using type = TypeSeq<Tags...>;
50template <
class T,
class U>
53template <
class... DDims,
class... ODDims>
61template <
class... ODDims>
66 return DiscreteVector<ODDims...>((get<ODDims>(lhs) * get<ODDims>(rhs))...);
69template <
class... DDims>
76 type_seq_is_unique_v<detail::TypeSeq<DDims...>>,
77 "The dimensions of a StridedDiscreteDomain must be unique");
80 using discrete_element_type = DiscreteElement<DDims...>;
85 DiscreteElement<DDims...> m_element_begin;
94 return sizeof...(DDims);
102 class = std::enable_if_t<(is_strided_discrete_domain_v<DDoms> && ...)>>
104 : m_element_begin(domains.front()...)
105 , m_extents(domains.extents()...)
106 , m_strides(domains.strides()...)
111
112
113
114
116 discrete_element_type
const& element_begin,
117 discrete_vector_type
const& extents,
118 discrete_vector_type
const& strides)
119 : m_element_begin(element_begin)
136 template <
class... ODims>
139 if (
empty() && other.empty()) {
142 return m_element_begin == other.m_element_begin && m_extents == other.m_extents
143 && m_strides == other.m_strides;
146#if !defined(__cpp_impl_three_way_comparison) || __cpp_impl_three_way_comparison < 201902L
148 template <
class...
ODims>
151 return !(*
this ==
other);
157 return (1UL * ... * get<DDims>(m_extents));
170 template <
class QueryDDim>
178 return m_element_begin;
183 return discrete_element_type(
184 (DiscreteElement<DDims>(m_element_begin)
185 + (get<DDims>(m_extents) - 1) * get<DDims>(m_strides))...);
209 discrete_vector_type n1,
210 discrete_vector_type n2)
const
218 return m_element_begin + prod(dvect, m_strides);
221 template <
class... DElems>
225 sizeof...(DDims) == (0 + ... + DElems::size()),
226 "Invalid number of dimensions");
227 static_assert((is_discrete_element_v<DElems> && ...),
"Expected DiscreteElements");
228 auto const contains_1d = [](DiscreteElementType
const i,
229 DiscreteElementType
const b,
230 DiscreteVectorElement
const n,
231 DiscreteVectorElement
const s) {
232 return (i >= b) && (i < (b + (n - 1) * s + 1)) && ((i - b) % s == 0);
234 DiscreteElement<DDims...>
const delem(delems...);
235 for (std::size_t i = 0; i <
rank(); ++i) {
237 detail::array(delem)[i],
238 detail::array(m_element_begin)[i],
239 detail::array(m_extents)[i],
240 detail::array(m_strides)[i])) {
247 template <
class... DElems>
249 DElems
const&... delems)
const noexcept
252 sizeof...(DDims) == (0 + ... + DElems::size()),
253 "Invalid number of dimensions");
254 static_assert((is_discrete_element_v<DElems> && ...),
"Expected DiscreteElements");
255 KOKKOS_ASSERT(contains(delems...))
257 ((DiscreteElement<DDims>(take<DDims>(delems...))
258 - DiscreteElement<DDims>(m_element_begin))
273 std::size_t N =
sizeof...(DDims),
274 class DDim0 = std::enable_if_t<N == 1, std::tuple_element_t<0, std::tuple<DDims...>>>>
281 std::size_t N =
sizeof...(DDims),
282 class DDim0 = std::enable_if_t<N == 1, std::tuple_element_t<0, std::tuple<DDims...>>>>
286 DDim0>(m_element_begin + m_extents * m_strides, m_strides);
290 std::size_t N =
sizeof...(DDims),
291 class DDim0 = std::enable_if_t<N == 1, std::tuple_element_t<0, std::tuple<DDims...>>>>
298 std::size_t N =
sizeof...(DDims),
299 class DDim0 = std::enable_if_t<N == 1, std::tuple_element_t<0, std::tuple<DDims...>>>>
303 DDim0>(m_element_begin + m_extents * m_strides, m_strides);
307 std::size_t N =
sizeof...(DDims),
308 class = std::enable_if_t<N == 1, std::tuple_element_t<0, std::tuple<DDims...>>>>
315 std::size_t N =
sizeof...(DDims),
316 class = std::enable_if_t<N == 1, std::tuple_element_t<0, std::tuple<DDims...>>>>
330 using discrete_element_type = DiscreteElement<>;
342 template <
class... ODDims>
349
350
351
352
354 [[
maybe_unused]] discrete_element_type
const& element_begin,
377#if !defined(__cpp_impl_three_way_comparison) || __cpp_impl_three_way_comparison < 201902L
381 return !(*
this ==
other);
473template <
class... QueryDDims,
class... DDims>
483struct ConvertTypeSeqToStridedDiscreteDomain;
485template <
class... DDims>
486struct ConvertTypeSeqToStridedDiscreteDomain<detail::TypeSeq<DDims...>>
492using convert_type_seq_to_strided_discrete_domain_t =
493 typename ConvertTypeSeqToStridedDiscreteDomain<T>::type;
498template <
class... DDimsA,
class... DDimsB>
503 using TagSeqA = detail::TypeSeq<DDimsA...>;
504 using TagSeqB = detail::TypeSeq<DDimsB...>;
506 using type_seq_r = type_seq_remove_t<TagSeqA, TagSeqB>;
507 return detail::convert_type_seq_to_strided_discrete_domain_t<type_seq_r>(DDom_a);
513template <
class... DDimsB,
class... DDimsA>
517 using TagSeqA = detail::TypeSeq<DDimsA...>;
518 using TagSeqB = detail::TypeSeq<DDimsB...>;
520 using type_seq_r = type_seq_remove_t<TagSeqA, TagSeqB>;
521 return detail::convert_type_seq_to_strided_discrete_domain_t<type_seq_r>(DDom_a);
527template <
typename DDim1,
typename DDim2,
typename DDimA,
typename... DDimsB>
528KOKKOS_FUNCTION
constexpr std::conditional_t<
529 std::is_same_v<DDimA, DDim1>,
536 if constexpr (std::is_same_v<DDimA, DDim1>) {
546template <
typename DDim1,
typename DDim2,
typename... DDimsA,
typename... DDimsB>
552 using TagSeqA = detail::TypeSeq<DDimsA...>;
553 using TagSeqB = detail::TypeSeq<DDim1>;
554 using TagSeqC = detail::TypeSeq<DDim2>;
556 using type_seq_r =
ddc::type_seq_replace_t<TagSeqA, TagSeqB, TagSeqC>;
557 return ddc::detail::convert_type_seq_to_strided_discrete_domain_t<type_seq_r>(
558 detail::replace_dim_of_1d<
565template <
class... QueryDDims,
class... DDims>
572template <
class... QueryDDims,
class... DDims>
579template <
class... QueryDDims,
class... DDims>
590 DiscreteElement<DDim> m_value = DiscreteElement<DDim>();
595 using iterator_category = std::random_access_iterator_tag;
597 using value_type = DiscreteElement<DDim>;
599 using difference_type = std::ptrdiff_t;
604 DiscreteElement<DDim> value,
644 if (n >=
static_cast<difference_type>(0)) {
645 m_value +=
static_cast<DiscreteElementType>(n) * m_stride;
647 m_value -=
static_cast<DiscreteElementType>(-n) * m_stride;
654 if (n >=
static_cast<difference_type>(0)) {
655 m_value -=
static_cast<DiscreteElementType>(n) * m_stride;
657 m_value +=
static_cast<DiscreteElementType>(-n) * m_stride;
664 return m_value + n * m_stride;
671 return xx.m_value == yy.m_value;
674#if !defined(__cpp_impl_three_way_comparison) || __cpp_impl_three_way_comparison < 201902L
688 return xx.m_value < yy.m_value;
737 return (yy.m_value > xx.m_value) ? (-
static_cast<difference_type>(yy.m_value - xx.m_value))
738 : (xx.m_value - yy.m_value);
KOKKOS_DEFAULTED_FUNCTION constexpr DiscreteElement()=default
KOKKOS_FUNCTION constexpr bool operator!=(DiscreteVector< OTags... > const &rhs) const noexcept
KOKKOS_DEFAULTED_FUNCTION constexpr DiscreteVector()=default
static KOKKOS_FUNCTION DiscreteVector distance_from_front() noexcept
KOKKOS_DEFAULTED_FUNCTION StridedDiscreteDomain & operator=(StridedDiscreteDomain &&x)=default
static KOKKOS_FUNCTION constexpr std::size_t size()
KOKKOS_FUNCTION constexpr StridedDiscreteDomain(discrete_element_type const &element_begin, discrete_vector_type const &size, discrete_vector_type const &strides)
Construct a StridedDiscreteDomain starting from element_begin with size points.
static KOKKOS_FUNCTION bool contains(DiscreteElement<>) noexcept
KOKKOS_FUNCTION constexpr StridedDiscreteDomain remove_first(discrete_vector_type n) const
static KOKKOS_FUNCTION constexpr discrete_element_type front() noexcept
KOKKOS_FUNCTION constexpr StridedDiscreteDomain remove(discrete_vector_type n1, discrete_vector_type n2) const
static KOKKOS_FUNCTION bool contains() noexcept
KOKKOS_FUNCTION constexpr StridedDiscreteDomain remove_last(discrete_vector_type n) const
KOKKOS_FUNCTION constexpr StridedDiscreteDomain take_last(discrete_vector_type n) const
static KOKKOS_FUNCTION constexpr discrete_vector_type extents() noexcept
static KOKKOS_FUNCTION constexpr std::size_t rank()
KOKKOS_DEFAULTED_FUNCTION StridedDiscreteDomain(StridedDiscreteDomain &&x)=default
static KOKKOS_FUNCTION DiscreteVector distance_from_front(DiscreteElement<>) noexcept
KOKKOS_DEFAULTED_FUNCTION constexpr StridedDiscreteDomain()=default
KOKKOS_FUNCTION constexpr operator bool()
static KOKKOS_FUNCTION constexpr bool empty() noexcept
KOKKOS_DEFAULTED_FUNCTION StridedDiscreteDomain(StridedDiscreteDomain const &x)=default
KOKKOS_FUNCTION constexpr DiscreteElement operator()(DiscreteVector<> const &) const noexcept
static KOKKOS_FUNCTION constexpr discrete_element_type back() noexcept
KOKKOS_FUNCTION constexpr bool operator==(StridedDiscreteDomain const &other) const
KOKKOS_DEFAULTED_FUNCTION ~StridedDiscreteDomain()=default
KOKKOS_FUNCTION constexpr StridedDiscreteDomain take_first(discrete_vector_type n) const
KOKKOS_FUNCTION constexpr StridedDiscreteDomain(StridedDiscreteDomain< ODDims... > const &domain)
KOKKOS_DEFAULTED_FUNCTION StridedDiscreteDomain & operator=(StridedDiscreteDomain const &x)=default
KOKKOS_DEFAULTED_FUNCTION StridedDiscreteDomain & operator=(StridedDiscreteDomain const &x)=default
KOKKOS_FUNCTION constexpr discrete_vector_type extents() const noexcept
KOKKOS_FUNCTION constexpr operator bool()
KOKKOS_FUNCTION constexpr StridedDiscreteDomain take_first(discrete_vector_type n) const
KOKKOS_FUNCTION constexpr DiscreteVector< QueryDDim > extent() const noexcept
KOKKOS_FUNCTION constexpr discrete_element_type front() const noexcept
KOKKOS_FUNCTION bool contains(DElems const &... delems) const noexcept
KOKKOS_FUNCTION constexpr std::size_t size() const
KOKKOS_FUNCTION auto cend() const
KOKKOS_FUNCTION constexpr StridedDiscreteDomain(DDoms const &... domains)
Construct a StridedDiscreteDomain by copies and merge of domains.
KOKKOS_FUNCTION DiscreteVector< DDims... > distance_from_front(DElems const &... delems) const noexcept
KOKKOS_DEFAULTED_FUNCTION StridedDiscreteDomain(StridedDiscreteDomain &&x)=default
KOKKOS_FUNCTION constexpr discrete_vector_type strides() const noexcept
KOKKOS_DEFAULTED_FUNCTION StridedDiscreteDomain & operator=(StridedDiscreteDomain &&x)=default
KOKKOS_FUNCTION constexpr StridedDiscreteDomain remove(discrete_vector_type n1, discrete_vector_type n2) const
KOKKOS_FUNCTION constexpr StridedDiscreteDomain remove_first(discrete_vector_type n) const
KOKKOS_FUNCTION constexpr discrete_element_type back() const noexcept
KOKKOS_DEFAULTED_FUNCTION StridedDiscreteDomain()=default
KOKKOS_FUNCTION constexpr DiscreteElement< DDims... > operator()(DiscreteVector< DDims... > const &dvect) const noexcept
friend class StridedDiscreteDomain
KOKKOS_FUNCTION auto begin() const
KOKKOS_FUNCTION auto end() const
KOKKOS_FUNCTION constexpr StridedDiscreteDomain remove_last(discrete_vector_type n) const
KOKKOS_FUNCTION constexpr StridedDiscreteDomain take_last(discrete_vector_type n) const
KOKKOS_DEFAULTED_FUNCTION ~StridedDiscreteDomain()=default
KOKKOS_DEFAULTED_FUNCTION StridedDiscreteDomain(StridedDiscreteDomain const &x)=default
KOKKOS_FUNCTION constexpr bool operator==(StridedDiscreteDomain< ODims... > const &other) const
KOKKOS_FUNCTION constexpr decltype(auto) operator[](std::size_t n)
static KOKKOS_FUNCTION constexpr std::size_t rank()
KOKKOS_FUNCTION auto cbegin() const
KOKKOS_FUNCTION constexpr bool empty() const noexcept
KOKKOS_FUNCTION constexpr decltype(auto) operator[](std::size_t n) const
KOKKOS_FUNCTION constexpr StridedDiscreteDomain(discrete_element_type const &element_begin, discrete_vector_type const &extents, discrete_vector_type const &strides)
Construct a StridedDiscreteDomain starting from element_begin with size points.
The top-level namespace of DDC.
KOKKOS_FUNCTION constexpr auto remove_dims_of(StridedDiscreteDomain< DDimsA... > const &DDom_a, StridedDiscreteDomain< DDimsB... > const &DDom_b) noexcept
KOKKOS_FUNCTION constexpr DiscreteElement< QueryDDims... > front(StridedDiscreteDomain< DDims... > const &domain) noexcept
KOKKOS_FUNCTION constexpr DiscreteVector< QueryDDims... > extents(StridedDiscreteDomain< DDims... > const &domain) noexcept
KOKKOS_FUNCTION constexpr DiscreteElement< QueryDDims... > back(StridedDiscreteDomain< DDims... > const &domain) noexcept
KOKKOS_FUNCTION constexpr StridedDiscreteDomain< QueryDDims... > select(StridedDiscreteDomain< DDims... > const &domain)
KOKKOS_FUNCTION constexpr auto remove_dims_of(StridedDiscreteDomain< DDimsA... > const &DDom_a) noexcept
Remove the dimensions DDimsB from DDom_a.
constexpr bool is_strided_discrete_domain_v
KOKKOS_FUNCTION DiscreteVector< ODDims... > prod(DiscreteVector< ODDims... > const &lhs, DiscreteVector< ODDims... > const &rhs) noexcept
KOKKOS_FUNCTION constexpr auto replace_dim_of(StridedDiscreteDomain< DDimsA... > const &DDom_a, StridedDiscreteDomain< DDimsB... > const &DDom_b) noexcept
friend KOKKOS_FUNCTION constexpr StridedDiscreteDomainIterator operator-(StridedDiscreteDomainIterator i, difference_type n)
KOKKOS_FUNCTION constexpr DiscreteElement< DDim > operator*() const noexcept
KOKKOS_FUNCTION constexpr StridedDiscreteDomainIterator & operator++()
friend KOKKOS_FUNCTION constexpr StridedDiscreteDomainIterator operator+(difference_type n, StridedDiscreteDomainIterator i)
KOKKOS_FUNCTION constexpr StridedDiscreteDomainIterator & operator-=(difference_type n)
KOKKOS_FUNCTION constexpr StridedDiscreteDomainIterator operator++(int)
friend KOKKOS_FUNCTION constexpr bool operator<(StridedDiscreteDomainIterator const &xx, StridedDiscreteDomainIterator const &yy)
KOKKOS_DEFAULTED_FUNCTION StridedDiscreteDomainIterator()=default
KOKKOS_FUNCTION constexpr StridedDiscreteDomainIterator operator--(int)
friend KOKKOS_FUNCTION constexpr bool operator==(StridedDiscreteDomainIterator const &xx, StridedDiscreteDomainIterator const &yy)
KOKKOS_FUNCTION constexpr StridedDiscreteDomainIterator(DiscreteElement< DDim > value, DiscreteVector< DDim > stride)
KOKKOS_FUNCTION constexpr StridedDiscreteDomainIterator & operator+=(difference_type n)
KOKKOS_FUNCTION constexpr DiscreteElement< DDim > operator[](difference_type n) const
friend KOKKOS_FUNCTION constexpr difference_type operator-(StridedDiscreteDomainIterator const &xx, StridedDiscreteDomainIterator const &yy)
KOKKOS_FUNCTION constexpr StridedDiscreteDomainIterator & operator--()
friend KOKKOS_FUNCTION constexpr bool operator>=(StridedDiscreteDomainIterator const &xx, StridedDiscreteDomainIterator const &yy)
friend KOKKOS_FUNCTION constexpr StridedDiscreteDomainIterator operator+(StridedDiscreteDomainIterator i, difference_type n)
friend KOKKOS_FUNCTION constexpr bool operator>(StridedDiscreteDomainIterator const &xx, StridedDiscreteDomainIterator const &yy)
friend KOKKOS_FUNCTION constexpr bool operator!=(StridedDiscreteDomainIterator const &xx, StridedDiscreteDomainIterator const &yy)
friend KOKKOS_FUNCTION constexpr bool operator<=(StridedDiscreteDomainIterator const &xx, StridedDiscreteDomainIterator const &yy)