libhatchet
Loading...
Searching...
No Matches
hxvector.hpp
Go to the documentation of this file.
1#pragma once
2// SPDX-FileCopyrightText: © 2017-2026 Adrian Johnston.
3// SPDX-License-Identifier: MIT
4// This file is licensed under the MIT license found in the LICENSE.md file.
5
10
11#include "libhatchet.h"
12
13// HX_USE_MACROS_WITH_MODULE allows including macros alongside the module.
14#if HX_USE_MACROS_WITH_MODULE
15#error Header does not provide macros alone.
16#endif
17
18#include "hxallocator.hpp"
19#include "hxsort.hpp"
21
22HX_NS_BEGIN_
23
24#if HX_CPLUSPLUS >= 202002L
25
30template<typename T_>
31concept hxvector_concept_ = requires(T_& x_) {
32 sizeof(T_);
33 { x_.~T_() };
34};
35#else
36#define hxvector_concept_ typename
37#endif
38
40// Internal. Extends the array using placement new when assigned to.
41template<typename array_t_>
42class hxarray_back_inserter_ {
43public:
44 // Internal. Extends the array using placement new when assigned to.
45 template<typename arg_t_>
46 typename array_t_::value_type& operator=(arg_t_&& arg_) {
47 return m_x_.push_back(hxforward<arg_t_>(arg_));
48 }
49private:
50 friend array_t_;
51 hxarray_back_inserter_(array_t_& x_) : m_x_(x_) { }
52#if HX_CPLUSPLUS >= 201703L
53 // Copy elision is C++17.
54 hxarray_back_inserter_(const hxarray_back_inserter_& x_) = delete;
55#endif
56 // No address-of operator. It wouldn't be what was expected.
57 void operator&(void) const = delete;
58 array_t_& m_x_;
59};
61
81template<hxvector_concept_ T_, hxsize_t capacity_=hxallocator_dynamic_capacity>
82class hxvector : private hxallocator<T_, capacity_> {
83public:
85 using iterator = T_*;
86
88 using const_iterator = const T_*;
89
91 using value_type = T_;
92
95 explicit hxvector(void);
96
99 explicit hxvector(hxsize_t size_) noexcept;
100
104 explicit hxvector(hxsize_t size_, const T_& x_) noexcept;
105
108 hxvector(const hxvector& x_) noexcept;
109
112 template <hxsize_t capacity_x_>
114
119 hxvector(hxvector&& x_) noexcept;
120
128 template<typename other_value_t_, hxsize_t array_length_>
129 hxvector(const other_value_t_(&array_)[array_length_]) noexcept;
130
137 template <typename other_value_t_>
138 hxvector(std::initializer_list<other_value_t_> x_) noexcept;
139
141 ~hxvector(void) noexcept;
142
146 void operator=(const hxvector& x_) noexcept;
147
151 template <hxsize_t capacity_x_>
152 void operator=(const hxvector<T_, capacity_x_>& x_) noexcept;
153
158 void operator=(hxvector&& x_) noexcept;
159
167 template<typename other_value_t_, hxsize_t array_length_>
168 void operator=(const other_value_t_(&array_)[array_length_]) noexcept;
169
172 const T_& operator[](hxsize_t index_) const;
173
176 T_& operator[](hxsize_t index_);
177
182 void operator+=(const T_& x_) noexcept;
183
188 void operator+=(T_&& x_) noexcept;
189
193 template <hxsize_t capacity_x_>
194 void operator+=(const hxvector<T_, capacity_x_>& x_) noexcept;
195
199 template <hxsize_t capacity_x_>
201
207 hxarray_back_inserter_<hxvector<T_, capacity_>> operator*(void);
208
213 hxvector& operator++(void) { return *this; }
214
216 hxvector& operator++(int) { return *this; }
217
227 template<typename callable_t_>
228 hxattr_nodiscard bool all_of(callable_t_&& callable_) const;
229
231 template<typename callable_t_>
232 bool all_of(callable_t_&& callable_);
233
243 template<typename callable_t_>
244 hxattr_nodiscard bool any_of(callable_t_&& callable_) const;
245
247 template<typename callable_t_>
248 bool any_of(callable_t_&& callable_);
249
254 template <typename iter_t_>
255 void assign(iter_t_ begin_, iter_t_ end_) noexcept;
256
257#if HX_CPLUSPLUS >= 202002L
262 template <typename range_t_>
263 void assign_range(range_t_& range_) noexcept;
264
268 template <typename range_t_>
270 void assign_range(range_t_&& range_) noexcept;
271#endif
272
274 const T_& back(void) const;
275
277 T_& back(void);
278
280 const T_* begin(void) const { return this->data(); }
281
283 T_* begin(void) { return this->data(); }
284
288 hxattr_nodiscard const T_* binary_search(const T_& value_) const;
289
293 hxattr_nodiscard T_* binary_search(const T_& value_);
294
297
300 const T_* cbegin(void) const { return this->data(); }
301
303 const T_* cend(void) const { return m_end_; }
304
306 void clear(void) noexcept;
307
309 using hxallocator<T_, capacity_>::data;
310
314 template<typename... args_t_>
315 T_& emplace_back(args_t_&&... args_) noexcept;
316
320 template<hxsize_t capacity_x_>
322
325 hxattr_nodiscard bool empty(void) const { return m_end_ == this->data(); }
326
328 const T_* end(void) const { return m_end_; }
329
331 T_* end(void) { return m_end_; }
332
336 void erase(T_* pos_) noexcept hxattr_nonnull(2);
337
341 void erase(hxsize_t index_) noexcept;
342
351 template<typename callable_t_>
352 hxsize_t erase_if_unordered(callable_t_&& callable_) noexcept;
353
362 template<typename callable_t_>
363 hxsize_t erase_if_heap(callable_t_&& callable_) noexcept;
364
376 void erase_unordered(const T_* pos_) noexcept hxattr_nonnull(2);
377
381 void erase_unordered(hxsize_t index_) noexcept;
382
386 hxattr_nodiscard const T_* find(const T_& value_) const;
387
390 hxattr_nodiscard T_* find(const T_& value_);
391
401 template<typename callable_t_>
402 hxattr_nodiscard const T_* find_if(callable_t_&& callable_) const;
403
405 template<typename callable_t_>
406 hxattr_nodiscard T_* find_if(callable_t_&& callable_);
407
418 template<typename callable_t_>
419 void for_each(callable_t_&& callable_) const;
420
422 template<typename callable_t_>
423 void for_each(callable_t_&& callable_);
424
426 const T_& front(void) const;
427
429 T_& front(void);
430
434 hxattr_nodiscard bool full(void) const { return m_end_ == this->data() + this->capacity(); }
435
439 template<typename callable_t_>
440 void generate_n(hxsize_t size_, callable_t_&& callable_) noexcept;
441
444 hxattr_nodiscard const T_* get(hxsize_t index_) const;
445
449
458 template<typename ref_t_>
459 void insert(const T_* pos_, ref_t_&& x_) noexcept hxattr_nonnull(2);
460
466 template<typename ref_t_>
467 void insert(hxsize_t index_, ref_t_&& x_) noexcept;
468
470 void insertion_sort(void) noexcept;
471
476 template<hxsize_t capacity_x_>
478
480 void make_heap(void) noexcept;
481
484 hxattr_nodiscard hxsize_t max_size(void) const { return this->capacity(); }
485
488 template <hxsize_t capacity_x_>
490
493 void memset(int byte_=0x00);
494
496 void pop_back(void) noexcept;
497
501 void pop_heap(void) noexcept;
502
507 template<typename... args_t_>
508 T_& push_back(args_t_&&... args_) noexcept;
509
514 template<typename ref_t_>
515 T_& push_heap(ref_t_&& arg_) noexcept;
516
521 void reserve(hxsize_t size_,
523 hxalignment_t alignment_=hxalignment);
524
529 void resize(hxsize_t size_) noexcept;
530
535 void resize(hxsize_t size_, const T_& x_) noexcept;
536
538 hxattr_nodiscard hxsize_t size(void) const { return m_end_ - this->data(); }
539
541 hxattr_nodiscard hxsize_t size_bytes(void) const { return hxsizeof<T_>() * this->size(); }
542
544 void sort(void) noexcept;
545
550 void swap(hxvector& x_) noexcept;
551
552private:
553 void destruct_(T_* begin_, T_* end_) noexcept;
554 void* push_back_unconstructed_(void);
555
556 T_* m_end_;
557};
558
559// Without the "requires" keyword these end up being ambiguous.
560#if HX_CPLUSPLUS >= 202002L
561
564template<typename T_, hxsize_t capacity_x_, hxsize_t capacity_y_>
566 const hxvector<T_, capacity_y_>& y_) {
567 return x_.equal(y_);
568}
569
573template<typename T_, hxsize_t capacity_x_, hxsize_t capacity_y_>
575 const hxvector<T_, capacity_y_>& y_) {
576 return x_.less(y_);
577}
578
582template<typename T_>
587
588#endif // HX_CPLUSPLUS >= 202002L
589#include "detail/hxvector.inl"
590HX_NS_END_
const T * data(void) const
Returns a pointer to a const and potentially uninitialized array of T.
Definition hxallocator.hpp:96
hxallocator(void)
Does not allocate until reserve_storage is called.
Definition hxallocator.hpp:78
hxvector - Implements std::vector, std::inplace_vector and std::back_insert_iterator with a few thing...
Definition hxvector.hpp:82
hxvector(hxsize_t size_) noexcept
Constructs an array of a given size using T's default constructor.
hxsize_t max_size(void) const
Returns the capacity of the array or 0 if unallocated.
Definition hxvector.hpp:484
bool any_of(callable_t_ &&callable_)
A non-const version of any_of.
const T * begin(void) const
Returns a const T* to the beginning of the array.
Definition hxvector.hpp:280
const T & front(void) const
Returns a const reference to the first element in the array.
void swap(hxvector &x_) noexcept
Swap contents with a temporary array.
void resize(hxsize_t size_, const T &x_) noexcept
An overload with an initial value for new elements.
void insert(hxsize_t index_, ref_t_ &&x_) noexcept
Inserts the element at the offset indicated.
T & push_back(args_t_ &&... args_) noexcept
Appends an element to the end of the array.
T & emplace_back(args_t_ &&... args_) noexcept
Emplaces an element at the end of the array using forwarded arguments.
hxsize_t capacity(void) const
Returns the capacity of the array or 0 if unallocated.
void pop_back(void) noexcept
Removes the end element from the array.
void memset(int byte_=0x00)
Calls memset on the array.
T value_type
Publishes the value type. Doesn't end with _t because of the standard.
Definition hxvector.hpp:91
void insertion_sort(void) noexcept
Sorts the array with insertion sort using hxkey_less. (Non-standard.).
bool any_of(callable_t_ &&callable_) const
Returns true if the predicate returns true for any element and false otherwise.
T * binary_search(const T &value_)
Non-const version.
const T * find(const T &value_) const
Finds the first occurrence of value using hxkey_equal.
void generate_n(hxsize_t size_, callable_t_ &&callable_) noexcept
Appends size elements generated by invoking callable repeatedly.
void sort(void) noexcept
Sorts the array using hxkey_less. (Non-standard.).
void operator=(const other_value_t_(&array_)[array_length_]) noexcept
Assign from a C-style array.
T & push_heap(ref_t_ &&arg_) noexcept
Inserts an element into a max-heap.
void erase_unordered(const T *pos_) noexcept
Variant of erase that moves the end element down to replace the erased element.
~hxvector(void) noexcept
Destructs the array and destroys all elements.
T & operator[](hxsize_t index_)
Returns a reference to the element at the specified index.
const T * end(void) const
Returns a const T* to the end of the array.
Definition hxvector.hpp:328
bool less(const hxvector< T, capacity_x_ > &x_) const
Returns true if this array compares less than x using hxkey_equal and hxkey_less.
const T * find_if(callable_t_ &&callable_) const
Finds the first element for which the predicate returns true.
void for_each(callable_t_ &&callable_)
Non-const version of for_each.
void make_heap(void) noexcept
Converts the array into a max-heap using hxkey_less. (Non-standard.).
const T * get(hxsize_t index_) const
Returns a const T* to the element at index or hxnull otherwise.
hxsize_t erase_if_heap(callable_t_ &&callable_) noexcept
Removes elements for which the predicate returns true while preserving the max-heap property maintain...
T * get(hxsize_t index_)
Returns a T* to the element at index or hxnull otherwise.
void resize(hxsize_t size_) noexcept
Resizes the array to the specified size, constructing or destroying elements as needed.
bool all_of(callable_t_ &&callable_) const
Returns true if the predicate returns true for every element and false otherwise.
const T * binary_search(const T &value_) const
Performs a binary search using hxkey_less.
void erase(hxsize_t index_) noexcept
Erases the element indicated.
void assign(iter_t_ begin_, iter_t_ end_) noexcept
Assigns elements from a range defined by random access iterators.
const T * cend(void) const
Returns a const T* to the end of the array.
Definition hxvector.hpp:303
void operator+=(const T &x_) noexcept
Appends an element.
hxvector(hxvector &&x_) noexcept
Copy construct from a temporary.
T * find_if(callable_t_ &&callable_)
Non-const version of find_if.
void reserve(hxsize_t size_, hxsystem_allocator_t allocator_=hxsystem_allocator_current, hxalignment_t alignment_=hxalignment)
Reserves storage for at least the specified number of elements.
void clear(void) noexcept
Clears the array, destroying all elements.
bool full(void) const
Returns true when the array is full (size equals capacity).
Definition hxvector.hpp:434
hxvector(const hxvector< T, capacity_x_ > &x_) noexcept
Copy constructs an array.
void operator+=(const hxvector< T, capacity_x_ > &x_) noexcept
Appends the contents of another array.
bool all_of(callable_t_ &&callable_)
A non-const version of all_of.
T * find(const T &value_)
Non-const version of find using hxkey_equal.
void operator=(hxvector &&x_) noexcept
Swap contents with a temporary array using swap.
const T & operator[](hxsize_t index_) const
Returns a const reference to the element at the specified index.
const T & back(void) const
Returns a const reference to the last element in the array.
hxvector(void)
Constructs an empty array with a capacity of capacity.
T * iterator
Random access iterator.
Definition hxvector.hpp:85
const T * const_iterator
Const random access iterator.
Definition hxvector.hpp:88
hxvector(const hxvector &x_) noexcept
Copy constructs an array.
void erase_unordered(hxsize_t index_) noexcept
Variant of erase that moves the end element down to replace the erased element.
hxsize_t erase_if_unordered(callable_t_ &&callable_) noexcept
Removes elements for which the predicate returns true.
void assign_range(range_t_ &range_) noexcept
Assigns elements from a range referenced by an lvalue.
const T * cbegin(void) const
Returns a const T* to the beginning of the array (alias for begin).
Definition hxvector.hpp:300
bool empty(void) const
Returns true if the array is empty.
Definition hxvector.hpp:325
hxarray_back_inserter_< hxvector< T, capacity_ > > operator*(void)
Used to write code with pointer semantics that writes to either a pointer or a hxvector.
hxvector(const other_value_t_(&array_)[array_length_]) noexcept
Constructs from a C-style array.
hxvector(std::initializer_list< other_value_t_ > x_) noexcept
Pass values of std::initializer_list as initializers to an array of T.
T & back(void)
Returns a reference to the last element in the array.
void operator=(const hxvector< T, capacity_x_ > &x_) noexcept
Assigns the contents of another hxvector to this array.
void operator+=(hxvector< T, capacity_x_ > &&x_) noexcept
Appends the contents of another array.
void for_each(callable_t_ &&callable_) const
Calls a function, lambda, or std::function on each element.
void insert(const T *pos_, ref_t_ &&x_) noexcept
Inserts the element at the offset indicated.
T * end(void)
Returns a T* to the end of the array.
Definition hxvector.hpp:331
T * begin(void)
Returns a T* to the beginning of the array.
Definition hxvector.hpp:283
bool equal(const hxvector< T, capacity_x_ > &x_) const
Returns true if the arrays compare equivalent using hxkey_equal.
hxvector(hxsize_t size_, const T &x_) noexcept
Constructs an array of a given size by making copies of x.
void pop_heap(void) noexcept
Removes the first (maximum) element from a max-heap.
void operator+=(T &&x_) noexcept
Appends an element.
void operator=(const hxvector &x_) noexcept
Assigns the contents of another hxvector to this array.
hxvector & operator++(void)
Allows an array to be passed as a reference and then used as an output iterator similar to std::back_...
Definition hxvector.hpp:213
T & front(void)
Returns a reference to the first element in the array.
void memcpy(const hxvector< T, capacity_x_ > &x_)
Copies another hxvector using memcpy.
hxvector & operator++(int)
Postfix version.
Definition hxvector.hpp:216
hxsize_t size(void) const
Returns the number of elements in the array.
Definition hxvector.hpp:538
void assign_range(range_t_ &&range_) noexcept
Assigns elements from a temporary range.
hxsize_t size_bytes(void) const
Returns the number of bytes in the array. (Non-standard.).
Definition hxvector.hpp:541
void erase(T *pos_) noexcept
Erases the element indicated.
hxvector_concept - Concept smoke testing the hxvector element.
Definition hxvector.hpp:31
Similar to std::allocator.
Implements or includes std::initializer_list depending on HX_USE_LIBCXX.
@ hxsystem_allocator_current
hxsystem_allocator_current - Use current allocation scope.
Definition hxmemory_manager.h:82
int hxsystem_allocator_t
hxsystem_allocator_t - This is extendable by the application.
Definition hxmemory_manager.h:77
unsigned int hxalignment_t
hxalignment_t - A positive integer power of 2 for aligning allocations.
Definition hxmemory_manager.h:64
constexpr hxalignment_t hxalignment
hxalignment - The default alignment.
Definition hxmemory_manager.h:69
#define hxinline
hxinline - Force a function to be inlined into its callers.
Definition hxsettings.h:120
#define hxattr_nonnull(...)
hxattr_nonnull - Indicates that a function has args that should not be null.
Definition hxsettings.h:97
#define hxattr_nodiscard
hxattr_nodiscard - Indicates the caller should not discard the return value.
Definition hxsettings.h:89
#define hxattr_flatten
hxattr_flatten - Inline every call inside a function's body into it, recursively, regardless of the c...
Definition hxsettings.h:82
Standard sorting utilities.
constexpr T && hxforward(hxremove_reference_t< T > &&x_)
hxforward - Implements std::forward.
Definition hxutility.h:304
void hxswap_memcpy(T &x_, T &y_)
hxswap_memcpy - Exchanges the contents of x and y using memcpy and a stack temporary.
Definition hxutility.h:354
bool hxkey_less(const hxvector< T, capacity_x_ > &x_, const hxvector< T, capacity_y_ > &y_)
bool hxkey_less(hxvector<T>& x, hxvector<T>& y) - Compares the contents of x and y lexicographically ...
Definition hxvector.hpp:574
bool hxkey_equal(const hxvector< T, capacity_x_ > &x_, const hxvector< T, capacity_y_ > &y_)
bool hxkey_equal(hxvector<T>& x, hxvector<T>& y) - Compares the contents of x and y for equivalence.
Definition hxvector.hpp:565
void hxswap(hxvector< T, hxallocator_dynamic_capacity > &x_, hxvector< T, hxallocator_dynamic_capacity > &y_) noexcept
void hxswap(hxvector<T>& x, hxvector<T>& y) - Exchanges the contents of x and y.
Definition hxvector.hpp:583
Provides core macros, memory management and feature detection.
constexpr hxsize_t hxsizeof(void)
hxsizeof - Returns the size of a type or expression as hxsize_t.
Definition libhatchet.h:288
ptrdiff_t hxsize_t
hxsize_t - A signed size type, same as ssize_t or ptrdiff_t.
Definition libhatchet.h:209
static constexpr bool value
Definition hxutility.h:124