tetl 0.1.0
Embedded Template Library
Loading...
Searching...
No Matches
submdspan_extents.hpp
Go to the documentation of this file.
1// SPDX-License-Identifier: BSL-1.0
2// SPDX-FileCopyrightText: Copyright (C) 2024 Tobias Hienzsch
3
4#ifndef TETL_MDSPAN_SUBMDSPAN_EXTENTS_HPP
5#define TETL_MDSPAN_SUBMDSPAN_EXTENTS_HPP
6
7#include <etl/_cstddef/size_t.hpp>
8#include <etl/_mdspan/extents.hpp>
9#include <etl/_mdspan/full_extent.hpp>
10#include <etl/_mdspan/integral_constant_like.hpp>
11#include <etl/_mdspan/strided_slice.hpp>
12#include <etl/_span/dynamic_extent.hpp>
13#include <etl/_tuple/tuple_element.hpp>
14#include <etl/_type_traits/always_false.hpp>
15#include <etl/_type_traits/is_convertible.hpp>
16
17namespace etl {
18
19namespace detail {
20
21template <etl::size_t K, typename Extent, typename Sk>
22constexpr auto submdspan_static_extent()
23{
24 using IndexT = typename Extent::index_type;
25
26 if constexpr (Extent::static_extent(Extent::rank() - K) != etl::dynamic_extent) {
27 if constexpr (etl::is_convertible_v<Sk, etl::full_extent_t>) {
28 return Extent::static_extent(Extent::rank() - K);
29 } else if constexpr (index_pair_like<Sk, IndexT>) {
30 using FirstT = etl::tuple_element_t<0, Sk>;
31 using SecondT = etl::tuple_element_t<1, Sk>;
32 if constexpr (integral_constant_like<FirstT> and integral_constant_like<SecondT>) {
33 return de_ice(etl::tuple_element_t<1, Sk>()) - de_ice(etl::tuple_element_t<0, Sk>());
34 }
35 } else if constexpr (is_strided_slice<Sk>) {
36 using ExtT = typename Sk::extent_type;
37 using StrideT = typename Sk::stride_type;
38 if constexpr (integral_constant_like<ExtT> and not integral_constant_like<StrideT> and ExtT() == 0) {
39 return 0;
40 } else if constexpr (integral_constant_like<ExtT> and integral_constant_like<StrideT>) {
41 return 1 + (de_ice(ExtT()) - 1) / de_ice(StrideT());
42 }
43 }
44 }
45
47}
48
49template <etl::size_t K, typename Extents, size_t... NewExtents>
50struct submdspan_extents_builder {
51 template <typename Slice, typename... SlicesAndExtents>
52 static constexpr auto next(Extents const& ext, Slice const& /*unused*/, SlicesAndExtents... slicesAndExtents)
53 {
54 if constexpr (etl::is_convertible_v<Slice, etl::full_extent_t>) {
55 return submdspan_extents_builder<
56 K - 1,
57 Extents,
58 Extents::static_extent(Extents::rank() - K),
59 NewExtents...
60 >::next(ext, slicesAndExtents..., ext.extent(Extents::rank() - K));
61 } else if constexpr (etl::is_convertible_v<Slice, etl::size_t>) {
62 return submdspan_extents_builder<K - 1, Extents, NewExtents...>::next(ext, slicesAndExtents...);
63 } else if constexpr (is_strided_slice<Slice>) {
64 static_assert(etl::always_false<Slice>);
65 } else {
66 constexpr auto newStaticExt = submdspan_static_extent<K, Extents, Slice>();
67 return submdspan_extents_builder<K - 1, Extents, newStaticExt, NewExtents...>::next(
68 ext,
69 slicesAndExtents...
70 );
71 }
72 }
73};
74
75template <typename Extents, size_t... NewStaticExtents>
76struct submdspan_extents_builder<0, Extents, NewStaticExtents...> {
77 template <typename... NewExtents>
78 static constexpr auto next(Extents const& /*unused*/, NewExtents... newExts)
79 {
80 return etl::extents<typename Extents::index_type, NewStaticExtents...>(newExts...);
81 }
82};
83
84} // namespace detail
85
86template <typename IndexT, etl::size_t... Extents, typename... SliceSpecifiers>
87[[nodiscard]] constexpr auto submdspan_extents(etl::extents<IndexT, Extents...> const& ext, SliceSpecifiers... slices)
88 requires(sizeof...(slices) == etl::extents<IndexT, Extents...>::rank())
89{
90 using ext_t = etl::extents<IndexT, Extents...>;
91 return detail::submdspan_extents_builder<ext_t::rank(), ext_t>::next(ext, slices...);
92}
93
94} // namespace etl
95
96#endif // TETL_MDSPAN_SUBMDSPAN_EXTENTS_HPP
constexpr auto dynamic_extent
etl::dynamic_extent is a constant of type etl::size_t that is used to differentiate etl::span of stat...
Definition dynamic_extent.hpp:15
Definition adjacent_find.hpp:9
constexpr auto submdspan_extents(etl::extents< IndexT, Extents... > const &ext, SliceSpecifiers... slices)
Definition submdspan_extents.hpp:87
Definition extents.hpp:23
Definition full_extent.hpp:10