A user-defined submdspan_mapping return different mappings for the same kind of slice. "Same kind of slice" means, for example, two different types that both model index-pair-like<index_type>.
This matters more given P2769R3 (get_element customization point object), which extends the definition of index-pair-like to include "anything for which get_element works." However, even the current definition of index-pair-like includes different Standard class templates, such as pair, tuple, array, and even complex. The following example shows a custom layout whose submdspan_mapping function returns a different layout mapping type, depending on whether the first slice is std::pair or some other index-pair-like type.
template<class T>
constexpr bool is_std_pair_v(T&&)
template<class First, class Second>
constexpr bool is_std_pair_v<std::pair<First, Second>> = true;
class custom_layout_1 {
template<class Extents>
class mapping { /* ... */ };
};
class custom_layout_2 {
template<class Extents>
class mapping { /* ... */ };
};
class custom_layout_3 {
template<class Extents>
class mapping {
// ...
template<class... SliceSpecifiers>
friend constexpr auto submdspan_mapping(
const mapping& src, SliceSpecifiers... slices) {
using return_type = std::conditional_t<
is_std_pair_v<std::remove_cvref_t<SliceSpecifiers...[0]>>,
typename custom_layout_1::template mapping<Extents>;
typename custom_layout_2::template mapping<Extents>
>;
return return_type{submdspan_extents(src.extents(), slices...)};
}
};
};
Is this really a problem?
submdspan's wording (specifically, [mdspan.sub.sub] 5.2 and 5.3) implicitly describes the behavior of submdspan_mapping. It doesn't specify the return type of submdspan_mapping (other than to say it's a layout mapping with the same extents as submdspan_extents would have produced, given the input extents and slice specifiers). However, it does spell out the result mapping's extents() and the behavior of its operator(). The effect is that the result of submdspan views the expected subset of elements of the input mdspan, regardless of the type of the result's layout mapping.
The issue
A user-defined
submdspan_mapping
return different mappings for the same kind of slice. "Same kind of slice" means, for example, two different types that both modelindex-pair-like
<index_type>
.This matters more given P2769R3 (
get_element
customization point object), which extends the definition ofindex-pair-like
to include "anything for whichget_element
works." However, even the current definition ofindex-pair-like
includes different Standard class templates, such aspair
,tuple
,array
, and evencomplex
. The following example shows a custom layout whosesubmdspan_mapping
function returns a different layout mapping type, depending on whether the first slice isstd::pair
or some otherindex-pair-like
type.Is this really a problem?
submdspan
's wording (specifically, [mdspan.sub.sub] 5.2 and 5.3) implicitly describes the behavior ofsubmdspan_mapping
. It doesn't specify the return type ofsubmdspan_mapping
(other than to say it's a layout mapping with the same extents assubmdspan_extents
would have produced, given the input extents and slice specifiers). However, it does spell out the result mapping'sextents()
and the behavior of itsoperator()
. The effect is that the result ofsubmdspan
views the expected subset of elements of the inputmdspan
, regardless of the type of the result's layout mapping.