[mdspan.sub] (original) (raw)

23 Containers library [containers]

23.7 Views [views]

23.7.3 Multidimensional access [views.multidim]

23.7.3.7 submdspan [mdspan.sub]


23.7.3.7.1 Overview [mdspan.sub.overview]

23.7.3.7.2 strided_slice [mdspan.sub.strided.slice]

23.7.3.7.3 submdspan_mapping_result [mdspan.sub.map.result]

23.7.3.7.4 Exposition-only helpers [mdspan.sub.helpers]

23.7.3.7.5 submdspan_extents function [mdspan.sub.extents]

23.7.3.7.6 Specializations of submdspan_mapping [mdspan.sub.map]

23.7.3.7.6.1 Common [mdspan.sub.map.common]

23.7.3.7.6.2 layout_left specialization of submdspan_mapping [mdspan.sub.map.left]

23.7.3.7.6.3 layout_right specialization of submdspan_mapping [mdspan.sub.map.right]

23.7.3.7.6.4 layout_stride specialization of submdspan_mapping [mdspan.sub.map.stride]

23.7.3.7.6.5 layout_left_padded specialization of submdspan_mapping [mdspan.sub.map.leftpad]

23.7.3.7.6.6 layout_right_padded specialization of submdspan_mapping [mdspan.sub.map.rightpad]

23.7.3.7.7 submdspan function template [mdspan.sub.sub]


23.7.3.7.1 Overview [mdspan.sub.overview]

The submdspan facilities create a new mdspanviewing a subset of elements of an existing input mdspan.

The subset viewed by the created mdspan is determined by the SliceSpecifier arguments.

For each function defined in [mdspan.sub] that takes a parameter pack named slices as an argument:

23.7.3.7.2 strided_slice [mdspan.sub.strided.slice]

strided_slice represents a set ofextent regularly spaced integer indices.

The indices start at offset, and increase by increments of stride.

namespace std { template<class OffsetType, class ExtentType, class StrideType> struct strided_slice { using offset_type = OffsetType;using extent_type = ExtentType;using stride_type = StrideType;[[no_unique_address]] offset_type offset{};[[no_unique_address]] extent_type extent{};[[no_unique_address]] stride_type stride{};};}

strided_slice has the data members and special members specified above.

It has no base classes or members other than those specified.

Mandates: OffsetType, ExtentType, and StrideTypeare signed or unsigned integer types, or model integral-constant-like.

[Note 1:

strided_slice{.offset = 1, .extent = 10, .stride = 3}indicates the indices 1, 4, 7, and 10.

Indices are selected from the half-open interval [1, 1 + 10).

— _end note_]

23.7.3.7.3 submdspan_mapping_result [mdspan.sub.map.result]

Specializations of submdspan_mapping_resultare returned by overloads of submdspan_mapping.

namespace std { template<class LayoutMapping> struct submdspan_mapping_result { [[no_unique_address]] LayoutMapping mapping = LayoutMapping(); size_t offset{};};}

submdspan_mapping_result has the data members and special members specified above.

It has no base classes or members other than those specified.

23.7.3.7.4 Exposition-only helpers [mdspan.sub.helpers]

template<class T> constexpr T _de-ice_(T val) { return val; } template<[_integral-constant-like_](span.syn#concept:integral-constant-like "23.7.2.1 Header <span> synopsis [span.syn]") T> constexpr auto _de-ice_(T) { return T::value; } template<class IndexType, size_t k, class... SliceSpecifiers> constexpr IndexType _first_(SliceSpecifiers... slices);

Mandates: IndexType is a signed or unsigned integer type.

Let denote the following value:

Preconditions: is representable as a value of type IndexType.

Returns: extents<IndexType>​::​index-cast().

template<size_t k, class Extents, class... SliceSpecifiers> constexpr auto _last_(const Extents& src, SliceSpecifiers... slices);

Mandates: Extents is a specialization of extents.

Let index_type be typename Extents​::​index_type.

Let denote the following value:

Preconditions: is representable as a value of type index_type.

Returns: Extents​::​index-cast().

template<class IndexType, size_t N, class... SliceSpecifiers> constexpr array<IndexType, sizeof...(SliceSpecifiers)> _src-indices_(const array<IndexType, N>& indices, SliceSpecifiers... slices);

Mandates: IndexType is a signed or unsigned integer type.

Returns: An array<IndexType, sizeof...(SliceSpecifiers)> src_idx such that for each k in the range [0, sizeof...(SliceSpecifiers)),src_idx[k] equals

23.7.3.7.5 submdspan_extents function [mdspan.sub.extents]

template<class IndexType, size_t... Extents, class... SliceSpecifiers> constexpr auto submdspan_extents(const extents<IndexType, Extents...>& src, SliceSpecifiers... slices);

Constraints: sizeof...(slices) equals sizeof...(Extents).

Mandates: For each rank index k of src.extents(), exactly one of the following is true:

Preconditions: For each rank index k of src.extents(), all of the following are true:

Let SubExtents be a specialization of extents such that:

Returns: A value ext of type SubExtents such that for each kfor which _map-rank_[k] != dynamic_extent is true,ext.extent(_map-rank_[k]) equals:

23.7.3.7.6 Specializations of submdspan_mapping [mdspan.sub.map]

23.7.3.7.6.1 Common [mdspan.sub.map.common]

The following elements apply to all functions in [mdspan.sub.map].

Constraints: sizeof...(slices) equals extents_type​::​rank().

Mandates: For each rank index k of extents(), exactly one of the following is true:

Preconditions: For each rank index k of extents(), all of the following are true:

Let sub_ext be the result of submdspan_extents(extents(), slices...) and let SubExtents be decltype(sub_ext).

Let sub_strides be an array<SubExtents​::​index_type, SubExtents​::​rank()>such that for each rank index k of extents()for which _map-rank_[k] is not dynamic_extent,sub_strides[_map-rank_[k]] equals:

Let P be a parameter pack such that is_same_v<make_index_sequence<rank()>, index_sequence<P...>>is true.

If first_<index_type, k>(slices...)equals extents().extent(k)for any rank index k of extents(), then let offset be a value of type size_t equal to(*this).required_span_size().

Otherwise, let offset be a value of type size_t equal to(*this)(first_<index_type, P>(slices...)...).

Given a layout mapping type M, a type S is aunit-stride slice for M if

23.7.3.7.6.2 layout_left specialization of submdspan_mapping [mdspan.sub.map.left]

template<class Extents> template<class... SliceSpecifiers> constexpr auto layout_left::mapping<Extents>::_submdspan-mapping-impl_( SliceSpecifiers... slices) const -> _see below_;

Returns:

23.7.3.7.6.3 layout_right specialization of submdspan_mapping [mdspan.sub.map.right]

template<class Extents> template<class... SliceSpecifiers> constexpr auto layout_right::mapping<Extents>::_submdspan-mapping-impl_( SliceSpecifiers... slices) const -> _see below_;

Returns:

23.7.3.7.6.4 layout_stride specialization of submdspan_mapping [mdspan.sub.map.stride]

template<class Extents> template<class... SliceSpecifiers> constexpr auto layout_stride::mapping<Extents>::_submdspan-mapping-impl_( SliceSpecifiers... slices) const -> _see below_;

Returns:

23.7.3.7.6.5 layout_left_padded specialization of submdspan_mapping [mdspan.sub.map.leftpad]

template<class Extents> template<class... SliceSpecifiers> constexpr auto layout_left_padded::mapping<Extents>::_submdspan-mapping-impl_( SliceSpecifiers... slices) const -> _see below_;

Returns:

23.7.3.7.6.6 layout_right_padded specialization of submdspan_mapping [mdspan.sub.map.rightpad]

template<class Extents> template<class... SliceSpecifiers> constexpr auto layout_right_padded::mapping<Extents>::submdspan-mapping-impl( SliceSpecifiers... slices) const -> _see below_;

Returns:

23.7.3.7.7 submdspan function template [mdspan.sub.sub]

template<class ElementType, class Extents, class LayoutPolicy,class AccessorPolicy, class... SliceSpecifiers> constexpr auto submdspan( const mdspan<ElementType, Extents, LayoutPolicy, AccessorPolicy>& src, SliceSpecifiers... slices) -> _see below_;

Let index_type be typename Extents​::​index_type.

Let sub_map_offset be the result ofsubmdspan_mapping(src.mapping(), slices...).

[Note 1:

This invocation of submdspan_mappingselects a function call via overload resolution on a candidate set that includes the lookup set found by argument-dependent lookup ([basic.lookup.argdep]).

— _end note_]

Constraints:

Mandates:

Preconditions:

[Note 2:

These conditions ensure that the mapping returned by submdspan_mappingmatches the algorithmically expected index-mapping given the slice specifiers.

— _end note_]

Effects: Equivalent to:auto sub_map_result = submdspan_mapping(src.mapping(), slices...);return mdspan(src.accessor().offset(src.data_handle(), sub_map_result.offset), sub_map_result.mapping,typename AccessorPolicy::offset_policy(src.accessor()));

[Example 1:

Given a rank-3 mdspan grid3d representing a three-dimensional grid of regularly spaced points in a rectangular prism, the function zero_surface sets all elements on the surface of the 3-dimensional shape to zero.

It does so by reusing a function zero_2dthat takes a rank-2 mdspan.

template<class T, class E, class L, class A> void zero_2d(mdspan<T, E, L, A> a) { static_assert(a.rank() == 2);for (int i = 0; i < a.extent(0); i++) for (int j = 0; j < a.extent(1); j++) a[i, j] = 0;} template<class T, class E, class L, class A> void zero_surface(mdspan<T, E, L, A> grid3d) { static_assert(grid3d.rank() == 3); zero_2d(submdspan(grid3d, 0, full_extent, full_extent)); zero_2d(submdspan(grid3d, full_extent, 0, full_extent)); zero_2d(submdspan(grid3d, full_extent, full_extent, 0)); zero_2d(submdspan(grid3d, grid3d.extent(0) - 1, full_extent, full_extent)); zero_2d(submdspan(grid3d, full_extent, grid3d.extent(1) - 1, full_extent)); zero_2d(submdspan(grid3d, full_extent, full_extent, grid3d.extent(2) - 1));} — _end example_]