Skip to content

Commit 5edec50

Browse files
authored
Merge 2025-06 LWG Motion 11
P3480R6 std::simd is a range
2 parents d75f66d + 1ddaeac commit 5edec50

File tree

1 file changed

+276
-0
lines changed

1 file changed

+276
-0
lines changed

source/numerics.tex

Lines changed: 276 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16509,6 +16509,10 @@
1650916509
template<size_t N> requires (has_single_bit(N))
1651016510
constexpr flags<@\exposid{overaligned-flag}<N>@> flag_overaligned{};
1651116511

16512+
// \ref{simd.iterator}, Class template \exposid{simd-iterator}
16513+
template<class V>
16514+
class @\exposidnc{simd-iterator}@; // \expos
16515+
1651216516
// \ref{simd.class}, Class template \tcode{basic_simd}
1651316517
template<class T, class Abi = @\exposid{native-abi}@<T>> class basic_simd;
1651416518
template<class T, @\exposid{simd-size-type}@ N = @\exposid{simd-size-v}@<T, @\exposid{native-abi}@<T>>>
@@ -17204,6 +17208,262 @@
1720417208
specialization \tcode{\exposid{overaligned-flag}<std::min(N1, N2)>}.
1720517209
\end{itemdescr}
1720617210

17211+
\rSec2[simd.iterator]{Class template \exposid{simd-iterator}}
17212+
\begin{codeblock}
17213+
namespace std::datapar {
17214+
template<class V>
17215+
class @\exposidnc{simd-iterator}@ { // \expos
17216+
V* @\exposid{data_}@ = nullptr; // \expos
17217+
@\exposid{simd-size-type}@ @\exposidnc{offset_}@ = 0; // \expos
17218+
17219+
constexpr @\exposidnc{simd-iterator}@(V& d, @\exposidnc{simd-size-type}@ off) noexcept; // \expos
17220+
17221+
public:
17222+
using value_type = typename V::value_type;
17223+
using iterator_category = input_iterator_tag;
17224+
using iterator_concept = random_access_iterator_tag;
17225+
using difference_type = @\exposid{simd-size-type}@;
17226+
17227+
constexpr @\exposid{simd-iterator}@() = default;
17228+
17229+
constexpr @\exposid{simd-iterator}@(const @\exposid{simd-iterator}@&) = default;
17230+
constexpr @\exposid{simd-iterator}@& operator=(const @\exposid{simd-iterator}@&) = default;
17231+
17232+
constexpr @\exposid{simd-iterator}@(const @\exposid{simd-iterator}@<remove_const_t<V>>&) requires is_const_v<V>;
17233+
17234+
constexpr value_type operator*() const;
17235+
17236+
constexpr @\exposid{simd-iterator}@& operator++();
17237+
constexpr @\exposid{simd-iterator}@ operator++(int);
17238+
constexpr @\exposid{simd-iterator}@& operator--();
17239+
constexpr @\exposid{simd-iterator}@ operator--(int);
17240+
17241+
constexpr @\exposid{simd-iterator}@& operator+=(difference_type n);
17242+
constexpr @\exposid{simd-iterator}@& operator-=(difference_type n);
17243+
17244+
constexpr value_type operator[](difference_type n) const;
17245+
17246+
friend constexpr bool operator==(@\exposid{simd-iterator}@ a, @\exposid{simd-iterator}@ b) = default;
17247+
friend constexpr bool operator==(@\exposid{simd-iterator}@ a, default_sentinel_t) noexcept;
17248+
friend constexpr auto operator<=>(@\exposid{simd-iterator}@ a, @\exposid{simd-iterator}@ b);
17249+
17250+
friend constexpr @\exposid{simd-iterator}@ operator+(@\exposid{simd-iterator}@ i, difference_type n);
17251+
friend constexpr @\exposid{simd-iterator}@ operator+(difference_type n, @\exposid{simd-iterator}@ i);
17252+
friend constexpr @\exposid{simd-iterator}@ operator-(@\exposid{simd-iterator}@ i, difference_type n);
17253+
17254+
friend constexpr difference_type operator-(@\exposid{simd-iterator}@ a, @\exposid{simd-iterator}@ b);
17255+
friend constexpr difference_type operator-(@\exposid{simd-iterator}@ i, default_sentinel_t) noexcept;
17256+
friend constexpr difference_type operator-(default_sentinel_t, @\exposid{simd-iterator}@ i) noexcept;
17257+
};
17258+
}
17259+
\end{codeblock}
17260+
17261+
\begin{itemdecl}
17262+
constexpr @\exposid{simd-iterator}@(V& d, @\exposid{simd-size-type}@ off) noexcept;
17263+
\end{itemdecl}
17264+
17265+
\begin{itemdescr}
17266+
\pnum
17267+
\effects
17268+
Initializes \exposid{data_} with \tcode{addressof(d)} and \exposid{offset_} with \tcode{off}.
17269+
\end{itemdescr}
17270+
17271+
\begin{itemdecl}
17272+
constexpr @\exposid{simd-iterator}@(const @\exposid{simd-iterator}@<remove_const_t<V>>& i) requires is_const_v<V>;
17273+
\end{itemdecl}
17274+
17275+
\begin{itemdescr}
17276+
\pnum
17277+
\effects
17278+
Initializes \exposid{data_} with \tcode{i.\exposid{data_}} and \exposid{offset_} with \tcode{i.\exposid{offset_}}.
17279+
\end{itemdescr}
17280+
17281+
\begin{itemdecl}
17282+
constexpr value_type operator*() const;
17283+
\end{itemdecl}
17284+
17285+
\begin{itemdescr}
17286+
\pnum
17287+
\effects
17288+
Equivalent to: \tcode{return (*\exposid{data_})[\exposid{offset_}];}
17289+
\end{itemdescr}
17290+
17291+
\begin{itemdecl}
17292+
constexpr @\exposid{simd-iterator}@& operator++();
17293+
\end{itemdecl}
17294+
17295+
\begin{itemdescr}
17296+
\pnum
17297+
\effects
17298+
Equivalent to: \tcode{return *this += 1;}
17299+
\end{itemdescr}
17300+
17301+
\begin{itemdecl}
17302+
constexpr @\exposid{simd-iterator}@ operator++(int);
17303+
\end{itemdecl}
17304+
17305+
\begin{itemdescr}
17306+
\pnum
17307+
\effects
17308+
Equivalent to:
17309+
\begin{codeblock}
17310+
@\exposid{simd-iterator}@ tmp = *this;
17311+
*this += 1;
17312+
return tmp;
17313+
\end{codeblock}
17314+
\end{itemdescr}
17315+
17316+
\begin{itemdecl}
17317+
constexpr @\exposid{simd-iterator}@& operator--();
17318+
\end{itemdecl}
17319+
17320+
\begin{itemdescr}
17321+
\pnum
17322+
\effects
17323+
Equivalent to: \tcode{return *this -= 1;}
17324+
\end{itemdescr}
17325+
17326+
\begin{itemdecl}
17327+
constexpr @\exposid{simd-iterator}@ operator--(int);
17328+
\end{itemdecl}
17329+
17330+
\begin{itemdescr}
17331+
\pnum
17332+
\effects
17333+
Equivalent to:
17334+
\begin{codeblock}
17335+
@\exposid{simd-iterator}@ tmp = *this;
17336+
*this -= 1;
17337+
return tmp;
17338+
\end{codeblock}
17339+
\end{itemdescr}
17340+
17341+
\begin{itemdecl}
17342+
constexpr @\exposid{simd-iterator}@& operator+=(difference_type n);
17343+
\end{itemdecl}
17344+
17345+
\begin{itemdescr}
17346+
\pnum
17347+
\expects
17348+
\tcode{\exposid{offset_} + n} is in the range \crange{0}{V::size()}.
17349+
17350+
\pnum
17351+
\effects
17352+
Equivalent to:
17353+
\begin{codeblock}
17354+
@\exposid{offset_}@ += n;
17355+
return *this;
17356+
\end{codeblock}
17357+
\end{itemdescr}
17358+
17359+
\begin{itemdecl}
17360+
constexpr @\exposid{simd-iterator}@& operator-=(difference_type n);
17361+
\end{itemdecl}
17362+
17363+
\begin{itemdescr}
17364+
\pnum
17365+
\expects
17366+
\tcode{\exposid{offset_} - n} is in the range \crange{0}{V::size()}.
17367+
17368+
\pnum
17369+
\effects
17370+
Equivalent to:
17371+
\begin{codeblock}
17372+
@\exposid{offset_}@ -= n;
17373+
return *this;
17374+
\end{codeblock}
17375+
\end{itemdescr}
17376+
17377+
\begin{itemdecl}
17378+
constexpr value_type operator[](difference_type n) const;
17379+
\end{itemdecl}
17380+
17381+
\begin{itemdescr}
17382+
\pnum
17383+
\effects
17384+
Equivalent to: \tcode{return (*\exposid{data_})[\exposid{offset_} + n];}
17385+
\end{itemdescr}
17386+
17387+
\begin{itemdecl}
17388+
friend constexpr bool operator==(@\exposid{simd-iterator}@ i, default_sentinel_t) noexcept;
17389+
\end{itemdecl}
17390+
17391+
\begin{itemdescr}
17392+
\pnum
17393+
\effects
17394+
Equivalent to: \tcode{return i.\exposid{offset_} == V::size();}
17395+
\end{itemdescr}
17396+
17397+
\begin{itemdecl}
17398+
friend constexpr auto operator<=>(@\exposid{simd-iterator}@ a, @\exposid{simd-iterator}@ b);
17399+
\end{itemdecl}
17400+
17401+
\begin{itemdescr}
17402+
\pnum
17403+
\expects
17404+
\tcode{a.\exposid{data_} == b.\exposid{data_}} is \tcode{true}.
17405+
17406+
\pnum
17407+
\effects
17408+
Equivalent to: \tcode{return a.\exposid{offset_} <=> b.\exposid{offset_};}
17409+
\end{itemdescr}
17410+
17411+
\begin{itemdecl}
17412+
friend constexpr @\exposid{simd-iterator}@ operator+(@\exposid{simd-iterator}@ i, difference_type n);
17413+
friend constexpr @\exposid{simd-iterator}@ operator+(difference_type n, @\exposid{simd-iterator}@ i);
17414+
\end{itemdecl}
17415+
17416+
\begin{itemdescr}
17417+
\pnum
17418+
\effects
17419+
Equivalent to: \tcode{return i += n;}
17420+
\end{itemdescr}
17421+
17422+
\begin{itemdecl}
17423+
friend constexpr @\exposid{simd-iterator}@ operator-(@\exposid{simd-iterator}@ i, difference_type n);
17424+
\end{itemdecl}
17425+
17426+
\begin{itemdescr}
17427+
\pnum
17428+
\effects
17429+
Equivalent to: \tcode{return i -= n;}
17430+
\end{itemdescr}
17431+
17432+
\begin{itemdecl}
17433+
friend constexpr difference_type operator-(@\exposid{simd-iterator}@ a, @\exposid{simd-iterator}@ b);
17434+
\end{itemdecl}
17435+
17436+
\begin{itemdescr}
17437+
\pnum
17438+
\expects
17439+
\tcode{a.\exposid{data_} == b.\exposid{data_}} is \tcode{true}.
17440+
17441+
\pnum
17442+
\effects
17443+
Equivalent to: \tcode{return a.\exposid{offset_} - b.\exposid{offset_};}
17444+
\end{itemdescr}
17445+
17446+
\begin{itemdecl}
17447+
friend constexpr difference_type operator-(@\exposid{simd-iterator}@ i, default_sentinel_t) noexcept;
17448+
\end{itemdecl}
17449+
17450+
\begin{itemdescr}
17451+
\pnum
17452+
\effects
17453+
Equivalent to: \tcode{return i.\exposid{offset_} - V::size();}
17454+
\end{itemdescr}
17455+
17456+
17457+
\begin{itemdecl}
17458+
friend constexpr difference_type operator-(default_sentinel_t, @\exposid{simd-iterator}@ i) noexcept;
17459+
\end{itemdecl}
17460+
17461+
\begin{itemdescr}
17462+
\pnum
17463+
\effects
17464+
Equivalent to: \tcode{return V::size() - i.\exposid{offset_};}
17465+
\end{itemdescr}
17466+
1720717467
\rSec2[simd.class]{Class template \tcode{basic_simd}}
1720817468

1720917469
\rSec3[simd.overview]{Class template \tcode{basic_simd} overview}
@@ -17215,6 +17475,14 @@
1721517475
using value_type = T;
1721617476
using mask_type = basic_simd_mask<sizeof(T), Abi>;
1721717477
using abi_type = Abi;
17478+
using @\libmember{iterator}{basic_simd}@ = @\exposid{simd-iterator}@<basic_simd>;
17479+
using @\libmember{const_iterator}{basic_simd}@ = @\exposid{simd-iterator}@<const basic_simd>;
17480+
17481+
constexpr iterator @\libmember{begin}{basic_simd}@() noexcept { return {*this, 0}; }
17482+
constexpr const_iterator @\libmember{begin}{basic_simd}@() const noexcept { return {*this, 0}; }
17483+
constexpr const_iterator @\libmember{cbegin}{basic_simd}@() const noexcept { return {*this, 0}; }
17484+
constexpr default_sentinel_t @\libmember{end}{basic_simd}@() const noexcept { return {}; }
17485+
constexpr default_sentinel_t @\libmember{cend}{basic_simd}@() const noexcept { return {}; }
1721817486

1721917487
static constexpr integral_constant<@\exposid{simd-size-type}@, @\exposid{simd-size-v}@<T, Abi>> size {};
1722017488

@@ -19101,6 +19369,14 @@
1910119369
public:
1910219370
using value_type = bool;
1910319371
using abi_type = Abi;
19372+
using @\libmember{iterator}{basic_simd_mask}@ = @\exposid{simd-iterator}@<basic_simd_mask>;
19373+
using @\libmember{const_iterator}{basic_simd_mask}@ = @\exposid{simd-iterator}@<const basic_simd_mask>;
19374+
19375+
constexpr iterator @\libmember{begin}{basic_simd_mask}@() noexcept { return {*this, 0}; }
19376+
constexpr const_iterator @\libmember{begin}{basic_simd_mask}@() const noexcept { return {*this, 0}; }
19377+
constexpr const_iterator @\libmember{cbegin}{basic_simd_mask}@() const noexcept { return {*this, 0}; }
19378+
constexpr default_sentinel_t @\libmember{end}{basic_simd_mask}@() const noexcept { return {}; }
19379+
constexpr default_sentinel_t @\libmember{cend}{basic_simd_mask}@() const noexcept { return {}; }
1910419380

1910519381
static constexpr integral_constant<@\exposid{simd-size-type}@, @\exposid{simd-size-v}@<@\exposid{integer-from}@<Bytes>, Abi>>
1910619382
size {};

0 commit comments

Comments
 (0)