Files
2025-10-25 03:02:53 +03:00

5.4 KiB
Raw Permalink Blame History

[mdspan.sub.sub]

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.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;

1

#

Let index_type be typename Extents::index_type.

2

#

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

[Note 1:

This invocation of submdspan_mapping selects 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]

3

#

Constraints:

sizeof...(slices) equals Extents::rank(), and

the expression submdspan_mapping(src.mapping(), slices...) is well-formed when treated as an unevaluated operand.

4

#

Mandates:

  • (4.1)

    decltype(submdspan_mapping(src.mapping(), slices...)) is a specialization of submdspan_mapping_result.

  • (4.2)

    is_same_v<remove_cvref_t<decltype(sub_map_offset.mapping.extents())>,decltype(submdspan_extents(src.mapping(), slices...))> is true.

  • (4.3)

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

Sk models convertible_to<index_type>,

Sk models index-pair-like<index_type>,

is_convertible_v<Sk, full_extent_t> is true, or

Sk is a specialization of strided_slice.

5

#

Preconditions:

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

if Sk is a specialization of strided_slice + (5.1.1.1) sk.extent=0, or

+
      [(5.1.1.2)](#5.1.1.2)

sk.stride>0

0 ≤ first_<index_type, k>(slices...) ≤ last_(src.extents(), slices...) ≤ src.extent(k)

sub_map_offset.mapping.extents() == submdspan_extents(src.mapping(), slices...) is true; and

for each integer pack I which is a multidimensional index in sub_map_offset.mapping.extents(),sub_map_offset.mapping(I...) + sub_map_offset.offset == src.mapping()(src-indices(array{I...}, slices...)) is true.

[Note 2:

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

— end note]

6

#

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()));

7

#

[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_2d that takes a rank-2 mdspan.

// zero out all elements in an mdspantemplate<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;}// zero out just the surfacetemplate<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]