Iros
 
Loading...
Searching...
No Matches
span_fixed_size.h
Go to the documentation of this file.
1#pragma once
2
18#include "di/meta/compare.h"
19#include "di/meta/constexpr.h"
20#include "di/meta/core.h"
21#include "di/meta/language.h"
22#include "di/meta/operations.h"
23#include "di/meta/vocab.h"
24#include "di/types/size_t.h"
27#include "di/util/to_address.h"
34
35namespace di::vocab {
36template<typename T, types::size_t extent>
37struct Array;
38
39template<typename T, types::size_t extent>
40requires(extent != dynamic_extent)
42 : public meta::EnableView<Span<T, extent>>
43 , public meta::EnableBorrowedContainer<Span<T, extent>>
44 , public util::AddMemberGet<Span<T, extent>> {
45public:
46 using Element = T;
47
48 constexpr explicit Span()
49 requires(extent == 0)
50 = default;
51
52 template<concepts::ContiguousIterator Iter>
54 constexpr explicit Span(Iter first, types::size_t count) : m_data(util::to_address(first)) {
55 DI_ASSERT(count == extent);
56 }
57
58 template<concepts::ContiguousIterator Iter, concepts::SizedSentinelFor<Iter> Sent>
61 constexpr explicit Span(Iter it, Sent sent) : m_data(util::to_address(it)) {
62 DI_ASSERT(sent - it == extent);
63 }
64
65 template<types::size_t size>
66 requires(size == extent)
67 constexpr Span(T (&array)[size]) : m_data(array) {}
68
69 template<concepts::QualificationConvertibleTo<T> U, types::size_t size>
70 requires(size == extent)
71 constexpr Span(vocab::Array<U, size>& array) : m_data(array.data()) {}
72
73 template<typename U, types::size_t size>
75 constexpr Span(vocab::Array<U, size> const& array) : m_data(array.data()) {}
76
77 template<concepts::ContiguousContainer Con>
81 constexpr explicit Span(Con&& container) : m_data(container::data(container)) {
83 }
84
85 template<concepts::QualificationConvertibleTo<T> U, types::size_t other_extent>
86 requires((other_extent == dynamic_extent || extent == other_extent))
87 constexpr explicit(other_extent == dynamic_extent) Span(Span<U, other_extent> const& other) : m_data(other.data()) {
88 DI_ASSERT(other.size() == extent);
89 }
90
91 constexpr Span(Span const&) = default;
92
93 constexpr auto operator=(Span const&) -> Span& = default;
94
95 constexpr auto begin() const -> T* { return data(); }
96 constexpr auto end() const -> T* { return data() + extent; }
97
98 constexpr auto front() const -> T&
99 requires(extent > 0)
100 {
101 return *data();
102 }
103
104 constexpr auto back() const -> T& requires(extent > 0) { return *(end() - 1); }
105
106 constexpr auto at(types::size_t index) const -> vocab::Optional<T&> {
107 if (index >= extent) {
108 return nullopt;
109 }
110 return (*this)[index];
111 }
112
113 constexpr auto operator[](types::size_t index) const -> T& requires(extent > 0) {
114 DI_ASSERT(index < extent);
115 return data()[index];
116 }
117
118 constexpr auto data() const -> T* {
119 return m_data;
120 }
121
122 constexpr auto size() const -> types::size_t { return extent; }
123 constexpr auto size_bytes() const -> types::size_t { return sizeof(T) * extent; }
124
125 [[nodiscard]] constexpr auto empty() const -> bool { return extent == 0; }
126
127 constexpr auto first(types::size_t count) const -> Optional<Span<T>> {
128 if (count > extent) {
129 return nullopt;
130 }
131 return Span<T> { data(), count };
132 }
133
134 constexpr auto last(types::size_t count) const -> Optional<Span<T>> {
135 if (count > extent) {
136 return nullopt;
137 }
138 return Span<T> { end() - count, count };
139 }
140
141 constexpr auto subspan(types::size_t offset) const -> Optional<Span<T>> {
142 if (offset > extent) {
143 return nullopt;
144 }
145 return Span<T> { data() + offset, extent - offset };
146 }
147
148 constexpr auto subspan(types::size_t offset, types::size_t count) const -> Optional<Span<T>> {
149 if (offset + count > extent) {
150 return nullopt;
151 }
152 return Span<T> { data() + offset, count };
153 }
154
155 template<types::size_t count>
156 requires(count <= extent)
157 constexpr auto first() const {
158 return Span<T, count> { data(), count };
159 }
160
161 template<types::size_t count>
162 requires(count <= extent)
163 constexpr auto last() const {
164 return Span<T, count> { end() - count, count };
165 }
166
167 template<types::size_t offset, types::size_t count = dynamic_extent>
168 requires(offset <= extent && (count == dynamic_extent || offset + count <= extent))
169 constexpr auto subspan() const {
170 if constexpr (count == dynamic_extent) {
171 return Span<T, extent - offset> { data() + offset, end() };
172 } else {
173 return Span<T, count> { data() + offset, count };
174 }
175 }
176
177 template<typename U = meta::RemoveCV<T>>
179 constexpr auto to_owned() const -> Array<U, extent> {
180 return apply(
181 [](auto const&... args) {
182 return Array<U, extent> { args... };
183 },
184 *this);
185 }
186
187private:
188 constexpr friend auto operator==(Span a, Span b) -> bool
190 {
191 return container::equal(a, b);
192 }
193
194 constexpr friend auto operator<=>(Span a, Span b)
196 {
197 return container::compare(a, b);
198 }
199
200 template<concepts::ContiguousIterator It, concepts::SizedSentinelFor<It> Sent>
203 -> Span<T> {
204 return Span<T>(util::move(first), util::move(last));
205 }
206
207 template<types::size_t index>
208 requires(index < extent)
213
214 template<types::size_t index>
215 requires(index < extent)
220
222 return extent;
223 }
224
225 template<types::size_t index>
226 requires(index < extent)
228 return self[index];
229 }
230
231 T* m_data { nullptr };
232};
233
234template<typename T, types::size_t size>
236
237template<typename T, types::size_t size>
239
240template<typename T, types::size_t size>
242}
#define DI_ASSERT(...)
Definition assert_bool.h:7
Definition optional_forward_declaration.h:5
Definition span_forward_declaration.h:10
constexpr other_extent const & other
Definition span_fixed_size.h:88
constexpr Span(Con &&container)
Definition span_fixed_size.h:81
constexpr auto data() const -> T *
Definition span_fixed_size.h:118
constexpr Span(Iter it, Sent sent)
Definition span_fixed_size.h:61
constexpr auto size() const -> types::size_t
Definition span_fixed_size.h:122
constexpr friend auto tag_invoke(types::Tag< tuple_element >, types::InPlaceType< Span >, Constexpr< index >) -> InPlaceType< T >
Definition span_fixed_size.h:209
constexpr friend auto tag_invoke(types::Tag< util::get_in_place >, Constexpr< index >, Span self) -> T &
Definition span_fixed_size.h:227
constexpr friend auto operator<=>(Span a, Span b)
Definition span_fixed_size.h:194
constexpr friend auto tag_invoke(types::Tag< container::reconstruct >, InPlaceType< Span >, It first, Sent last) -> Span< T >
Definition span_fixed_size.h:202
constexpr Span(vocab::Array< U, size > &array)
Definition span_fixed_size.h:71
constexpr auto back() const -> T &requires(extent > 0)
Definition span_fixed_size.h:104
constexpr auto first() const
Definition span_fixed_size.h:157
constexpr auto last() const
Definition span_fixed_size.h:163
constexpr Span(vocab::Array< U, size > const &array)
Definition span_fixed_size.h:75
constexpr Span()=default
constexpr auto front() const -> T &requires(extent > 0)
Definition span_fixed_size.h:98
T Element
Definition span_fixed_size.h:46
constexpr auto end() const -> T *
Definition span_fixed_size.h:96
constexpr friend auto tag_invoke(types::Tag< tuple_size >, types::InPlaceType< Span >) -> types::size_t
Definition span_fixed_size.h:221
constexpr auto subspan(types::size_t offset, types::size_t count) const -> Optional< Span< T > >
Definition span_fixed_size.h:148
constexpr auto operator=(Span const &) -> Span &=default
constexpr Span(Span const &)=default
constexpr auto to_owned() const -> Array< U, extent >
Definition span_fixed_size.h:179
constexpr auto operator[](types::size_t index) const -> T &requires(extent > 0)
Definition span_fixed_size.h:113
constexpr auto at(types::size_t index) const -> vocab::Optional< T & >
Definition span_fixed_size.h:106
constexpr auto begin() const -> T *
Definition span_fixed_size.h:95
constexpr auto first(types::size_t count) const -> Optional< Span< T > >
Definition span_fixed_size.h:127
constexpr friend auto operator==(Span a, Span b) -> bool requires(concepts::EqualityComparable< T >)
Definition span_fixed_size.h:188
constexpr Span(Iter first, types::size_t count)
Definition span_fixed_size.h:54
constexpr auto empty() const -> bool
Definition span_fixed_size.h:125
constexpr friend auto tag_invoke(types::Tag< tuple_element >, types::InPlaceType< Span const >, Constexpr< index >) -> InPlaceType< T >
Definition span_fixed_size.h:216
constexpr auto subspan(types::size_t offset) const -> Optional< Span< T > >
Definition span_fixed_size.h:141
constexpr auto size_bytes() const -> types::size_t
Definition span_fixed_size.h:123
constexpr auto last(types::size_t count) const -> Optional< Span< T > >
Definition span_fixed_size.h:134
constexpr auto subspan() const
Definition span_fixed_size.h:169
constexpr Span(T(&array)[size])
Definition span_fixed_size.h:67
Definition vocab.h:27
Definition borrowed_container.h:8
Definition language.h:18
Definition operations.h:99
Definition operations.h:34
Definition compare.h:82
Definition language.h:110
Definition sized_container.h:8
Definition vocab.h:146
Definition compare.h:91
Definition sequence.h:12
constexpr auto size
Definition size.h:54
constexpr auto data
Definition data.h:51
constexpr auto equal
Definition equal.h:46
constexpr auto compare
Definition compare.h:40
Definition merge_interfaces.h:6
Definition method.h:5
std::size_t size_t
Definition size_t.h:12
di::meta::Decay< decltype(T)> Tag
Definition tag_invoke.h:28
Definition vocab.h:96
constexpr auto to_address
Definition to_address.h:22
Definition lazy.h:165
constexpr auto apply(F &&f, Tup &&tuple) -> decltype(detail::apply_impl(meta::MakeIndexSequence< meta::TupleSize< Tup > > {}, util::forward< F >(f), util::forward< Tup >(tuple)))
Definition apply.h:22
Span(Iter, SentOrSize) -> Span< meta::RemoveReference< meta::IteratorReference< Iter > > >
constexpr auto nullopt
Definition nullopt.h:15
constexpr auto dynamic_extent
Definition span_forward_declaration.h:7
constexpr auto size
Definition size.h:54
constexpr auto data
Definition data.h:51
constexpr auto count
Definition count.h:37
constexpr auto end
Definition end.h:47
A wrapper for a constexpr value.
Definition core.h:77
Definition in_place_type.h:5
Definition span_fixed_size.h:37
constexpr auto data() -> T *
Definition array.h:75