22 using const_pointer =
void const *;
24 static constexpr std::size_t extent = std::dynamic_extent;
26 constexpr ~void_span() =
default;
27 constexpr void_span()
noexcept =
default;
28 constexpr void_span(void_span
const&)
noexcept =
default;
29 constexpr void_span(void_span&&)
noexcept =
default;
30 constexpr void_span& operator=(void_span
const&)
noexcept =
default;
31 constexpr void_span& operator=(void_span&&)
noexcept =
default;
32 constexpr void_span(
void *
pointer,
size_t size) noexcept : _pointer(
pointer), _size(size)
37 template<
typename T, std::
size_t N>
38 constexpr void_span(
std::array<T, N>& rhs)
noexcept requires(not std::is_const_v<T>) : void_span(rhs.
data(), rhs.
size())
42 template<
typename T, std::
size_t N>
43 constexpr void_span(std::span<T, N>& rhs)
noexcept requires(not std::is_const_v<T>) : void_span(rhs.
data(), rhs.
size())
47 [[nodiscard]]
constexpr pointer data()
const noexcept
52 [[nodiscard]]
constexpr size_type size()
const noexcept
57 [[nodiscard]]
constexpr size_type size_bytes()
const noexcept
62 [[nodiscard]]
constexpr bool empty()
const noexcept
67 template<std::
size_t N>
68 [[nodiscard]]
constexpr void_span first()
const noexcept
74 [[nodiscard]]
constexpr void_span first(size_type n)
const noexcept
80 template<std::
size_t N>
81 [[nodiscard]]
constexpr void_span last()
const noexcept
87 [[nodiscard]]
constexpr void_span last(size_type n)
const noexcept
93 template<std::
size_t Offset, std::
size_t Count = std::dynamic_extent>
94 [[nodiscard]]
constexpr void_span subspan()
const noexcept
96 if constexpr (Count == std::dynamic_extent) {
100 hi_axiom((Offset + Count) <= _size);
105 [[nodiscard]]
constexpr void_span subspan(size_type offset, size_type count = std::dynamic_extent)
const noexcept
108 if (count == std::dynamic_extent) {
109 count = _size - offset;
116 template<
typename T,
size_t E = std::dynamic_extent>
117 [[nodiscard]]
constexpr friend std::span<T, E> as_span(void_span
const& rhs)
noexcept
119 if constexpr (E == std::dynamic_extent) {
120 hi_axiom(std::bit_cast<std::uintptr_t>(rhs._pointer) % std::alignment_of_v<T> == 0);
121 hi_axiom((rhs._size /
sizeof(T)) *
sizeof(T) == rhs._size);
122 return {
static_cast<T *
>(rhs._pointer), rhs._size /
sizeof(T)};
125 hi_axiom(std::bit_cast<std::uintptr_t>(rhs._pointer) % std::alignment_of_v<T> == 0);
126 hi_axiom(E *
sizeof(T) <= rhs._size);
127 return {
static_cast<T *
>(rhs._pointer), E};
131 template<
typename CharT,
typename Traits = std::
char_traits<CharT>>
132 [[nodiscard]]
constexpr friend std::basic_string_view<CharT, Traits> as_basic_string_view(void_span
const& rhs)
noexcept
134 hi_axiom(std::bit_cast<std::uintptr_t>(rhs._pointer) % std::alignment_of_v<CharT> == 0);
135 hi_axiom((rhs._size /
sizeof(CharT)) *
sizeof(CharT) == rhs._size);
136 return {
static_cast<CharT
const *
>(rhs._pointer), rhs._size /
sizeof(CharT)};
139 [[nodiscard]]
constexpr friend std::string_view as_string_view(void_span
const& rhs)
noexcept
141 return as_basic_string_view<char>(rhs);
144 [[nodiscard]]
constexpr friend bstring_view as_bstring_view(void_span
const& rhs)
noexcept
146 return as_basic_string_view<std::byte, byte_char_traits>(rhs);
154class const_void_span {
159 using const_pointer =
void const *;
161 static constexpr std::size_t extent = std::dynamic_extent;
163 constexpr ~const_void_span() =
default;
164 constexpr const_void_span()
noexcept =
default;
165 constexpr const_void_span(const_void_span
const&)
noexcept =
default;
166 constexpr const_void_span(const_void_span&&)
noexcept =
default;
167 constexpr const_void_span& operator=(const_void_span
const&)
noexcept =
default;
168 constexpr const_void_span& operator=(const_void_span&&)
noexcept =
default;
169 constexpr const_void_span(
void const *
pointer,
size_t size) noexcept : _pointer(
pointer), _size(size)
174 constexpr const_void_span(
void_span const& rhs) noexcept : const_void_span(rhs.data(), rhs.size()) {}
176 template<
typename T, std::
size_t N>
177 constexpr const_void_span(
std::array<T, N> const& rhs) noexcept : const_void_span(rhs.data(), rhs.size())
181 template<
typename T, std::
size_t N>
182 constexpr const_void_span(std::span<T, N>
const& rhs) noexcept : const_void_span(rhs.data(), rhs.size())
186 [[nodiscard]]
constexpr pointer data()
const noexcept
191 [[nodiscard]]
constexpr size_type size()
const noexcept
196 [[nodiscard]]
constexpr size_type size_bytes()
const noexcept
201 [[nodiscard]]
constexpr bool empty()
const noexcept
206 template<std::
size_t N>
207 [[nodiscard]]
constexpr const_void_span first()
const noexcept
210 return {_pointer, N};
213 [[nodiscard]]
constexpr const_void_span first(size_type n)
const noexcept
216 return {_pointer, n};
219 template<std::
size_t N>
220 [[nodiscard]]
constexpr const_void_span last()
const noexcept
226 [[nodiscard]]
constexpr const_void_span last(size_type n)
const noexcept
232 template<std::
size_t Offset, std::
size_t Count = std::dynamic_extent>
233 [[nodiscard]]
constexpr const_void_span subspan()
const noexcept
235 if constexpr (Count == std::dynamic_extent) {
239 hi_axiom((Offset + Count) <= _size);
244 [[nodiscard]]
constexpr const_void_span subspan(size_type offset, size_type count = std::dynamic_extent)
const noexcept
247 if (count == std::dynamic_extent) {
248 count = _size - offset;
255 template<
typename T,
size_t E = std::dynamic_extent>
256 [[nodiscard]]
constexpr friend std::span<T, E> as_span(const_void_span
const& rhs)
noexcept requires(std::is_const_v<T>)
258 if constexpr (E == std::dynamic_extent) {
259 hi_axiom(std::bit_cast<std::uintptr_t>(rhs._pointer) % std::alignment_of_v<T> == 0);
260 hi_axiom((rhs._size /
sizeof(T)) *
sizeof(T) == rhs._size);
261 return {
static_cast<T *
>(rhs._pointer), rhs._size /
sizeof(T)};
264 hi_axiom(std::bit_cast<std::uintptr_t>(rhs._pointer) % std::alignment_of_v<T> == 0);
265 hi_axiom(E *
sizeof(T) <= rhs._size);
266 return {
static_cast<T *
>(rhs._pointer), E};
270 template<
typename CharT,
typename Traits = std::
char_traits<CharT>>
271 [[nodiscard]]
constexpr friend std::basic_string_view<CharT, Traits> as_basic_string_view(const_void_span
const& rhs)
noexcept
273 hi_axiom(std::bit_cast<std::uintptr_t>(rhs._pointer) % std::alignment_of_v<CharT> == 0);
274 hi_axiom((rhs._size /
sizeof(CharT)) *
sizeof(CharT) == rhs._size);
275 return {
static_cast<CharT
const *
>(rhs._pointer), rhs._size /
sizeof(CharT)};
278 [[nodiscard]]
constexpr friend std::string_view as_string_view(const_void_span
const& rhs)
noexcept
280 return as_basic_string_view<char>(rhs);
283 [[nodiscard]]
constexpr friend bstring_view as_bstring_view(const_void_span
const& rhs)
noexcept
285 return as_basic_string_view<std::byte, byte_char_traits>(rhs);
#define hi_assert(expression,...)
Assert if expression is true.
Definition assert.hpp:199
#define hi_axiom(expression,...)
Specify an axiom; an expression that is true.
Definition assert.hpp:253
void * advance_bytes(void *ptr, std::ptrdiff_t distance) noexcept
Advance a pointer by a number of bytes.
Definition memory.hpp:191