[mdspan.layout.leftpad.overview]

# 23 Containers library [[containers]](./#containers)

## 23.7 Views [[views]](views#mdspan.layout.leftpad.overview)

### 23.7.3 Multidimensional access [[views.multidim]](views.multidim#mdspan.layout.leftpad.overview)

#### 23.7.3.4 Layout mapping [[mdspan.layout]](mdspan.layout#leftpad.overview)

#### 23.7.3.4.8 Class template layout_left_padded​::​mapping [[mdspan.layout.leftpad]](mdspan.layout.leftpad#overview)

#### 23.7.3.4.8.1 Overview [mdspan.layout.leftpad.overview]

[1](#1)

[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/containers.tex#L22947)

layout_left_padded provides a layout mapping
that behaves like layout_left​::​mapping,
except that the padding stride stride(1) can be greater than or equal to extent(0)[.](#1.sentence-1)

namespace std {template<size_t PaddingValue>template<class Extents>class layout_left_padded<PaddingValue>::mapping {public:static constexpr size_t padding_value = PaddingValue; using extents_type = Extents; using index_type = typename extents_type::index_type; using size_type = typename extents_type::size_type; using rank_type = typename extents_type::rank_type; using layout_type = layout_left_padded<PaddingValue>; private:static constexpr size_t *rank_* = extents_type::rank(); // *exposition only*static constexpr size_t *first-static-extent* = // *exposition only* extents_type::static_extent(0); // [[mdspan.layout.leftpad.expo]](mdspan.layout.leftpad.expo "23.7.3.4.8.2 Exposition-only members"), exposition-only membersstatic constexpr size_t *static-padding-stride* = *see below*; // *exposition only*public:// [[mdspan.layout.leftpad.cons]](mdspan.layout.leftpad.cons "23.7.3.4.8.3 Constructors"), constructorsconstexpr mapping() noexcept : mapping(extents_type{}) {}constexpr mapping(const mapping&) noexcept = default; constexpr mapping(const extents_type&); template<class OtherIndexType>constexpr mapping(const extents_type&, OtherIndexType); template<class OtherExtents>constexpr explicit(!is_convertible_v<OtherExtents, extents_type>) mapping(const layout_left::mapping<OtherExtents>&); template<class OtherExtents>constexpr explicit(extents_type::rank() > 0) mapping(const layout_stride::mapping<OtherExtents>&); template<class LayoutLeftPaddedMapping>constexpr explicit(*see below*) mapping(const LayoutLeftPaddedMapping&); template<class LayoutRightPaddedMapping>constexpr explicit(*see below*) mapping(const LayoutRightPaddedMapping&) noexcept; constexpr mapping& operator=(const mapping&) noexcept = default; // [[mdspan.layout.leftpad.obs]](mdspan.layout.leftpad.obs "23.7.3.4.8.4 Observers"), observersconstexpr const extents_type& extents() const noexcept { return *extents_*; }constexpr array<index_type, rank_> strides() const noexcept; constexpr index_type required_span_size() const noexcept; template<class... Indices>constexpr index_type operator()(Indices...) const noexcept; static constexpr bool is_always_unique() noexcept { return true; }static constexpr bool is_always_exhaustive() noexcept; static constexpr bool is_always_strided() noexcept { return true; }static constexpr bool is_unique() noexcept { return true; }constexpr bool is_exhaustive() const noexcept; static constexpr bool is_strided() noexcept { return true; }constexpr index_type stride(rank_type) const noexcept; template<class LayoutLeftPaddedMapping>friend constexpr bool operator==(const mapping&, const LayoutLeftPaddedMapping&) noexcept; private:// [[mdspan.layout.leftpad.expo]](mdspan.layout.leftpad.expo "23.7.3.4.8.2 Exposition-only members"), exposition-only members index_type *stride-1* = *static-padding-stride*; // *exposition only* extents_type *extents_*{}; // *exposition only*// [[mdspan.sub.map]](mdspan.sub.map "23.7.3.7.6 Specializations of submdspan_­mapping"), submdspan mapping specializationtemplate<class... SliceSpecifiers>constexpr auto *submdspan-mapping-impl*(SliceSpecifiers...) const // *exposition only*-> *see below*; template<class... SliceSpecifiers>friend constexpr auto submdspan_mapping(const mapping& src, SliceSpecifiers... slices) {return src.*submdspan-mapping-impl*(slices...); }};}

[2](#2)

[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/containers.tex#L23035)

If Extents is not a specialization of extents,
then the program is ill-formed[.](#2.sentence-1)

[3](#3)

[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/containers.tex#L23039)

layout_left_padded​::​mapping<E> is a trivially copyable type
that models [regular](concepts.object#concept:regular "18.6 Object concepts [concepts.object]") for each E[.](#3.sentence-1)

[4](#4)

[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/containers.tex#L23043)

Throughout [[mdspan.layout.leftpad]](mdspan.layout.leftpad "23.7.3.4.8 Class template layout_­left_­padded​::​mapping"),
let P_rank be the following
size *rank_* parameter pack of size_t values:

- [(4.1)](#4.1)

the empty parameter pack, if *rank_* equals zero;

- [(4.2)](#4.2)

otherwise, 0zu, if *rank_* equals one;

- [(4.3)](#4.3)

otherwise, the parameter pack 0zu, 1zu, …, *rank_*- 1[.](#4.sentence-1)

[5](#5)

[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/containers.tex#L23056)

*Mandates*: 

- [(5.1)](#5.1)

  If rank_dynamic() == 0 is true,
then the size of the multidimensional index space Extents() is representable as a value of type index_type[.](#5.1.sentence-1)

- [(5.2)](#5.2)

  padding_value is representable as a value of type index_type[.](#5.2.sentence-1)

- [(5.3)](#5.3)

  If
  * [(5.3.1)](#5.3.1)

*rank_* is greater than one,

  * [(5.3.2)](#5.3.2)

padding_value does not equal dynamic_extent, and

  * [(5.3.3)](#5.3.3)

*first-static-extent* does not equal dynamic_extent,

then *LEAST-MULTIPLE-AT-LEAST*(padding_value, *first-static-extent*) is representable as a value of type size_t, and
is representable as a value of type index_type[.](#5.3.sentence-1)

- [(5.4)](#5.4)

  If
  * [(5.4.1)](#5.4.1)

*rank_* is greater than one,

  * [(5.4.2)](#5.4.2)

padding_value does not equal dynamic_extent, and

  * [(5.4.3)](#5.4.3)

extents_type​::​static_extent(k) does not equal dynamic_extent for all k in the range [0, extents_type​::​rank()),

then the product of*LEAST-MULTIPLE-AT-LEAST*(padding_value, ext.static_extent(0)) and
all values ext.static_extent(k) with k in the range of [1, *rank_*)
is representable as a value of type size_t, and
is representable as a value of type index_type[.](#5.4.sentence-1)
