openMSX
static_vector.hh
Go to the documentation of this file.
1#ifndef STATIC_VECTOR_HH
2#define STATIC_VECTOR_HH
3
4#include <algorithm>
5#include <array>
6#include <cassert>
7#include <cstddef>
8#include <cstdint>
9#include <initializer_list>
10#include <limits>
11#include <span>
12#include <type_traits>
13
14// This is a _very_ minimal implementation of the following (we can easily
15// extend this when the need arises).
16//
17// static_vector
18// A dynamically-resizable vector with fixed capacity and embedded storage
19// http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2018/p0843r2.html
20//
21// For us the main purpose of this class is to use it during constexpr
22// (compile-time) calculations. Because for now, it's no yet possible to use
23// heap memory in constexpr functions (there are proposals to loosen this
24// restriction in future C++ standards).
25
26struct from_range_t {};
27inline constexpr from_range_t from_range;
28
29template<typename T, size_t N>
31{
32 using SizeType =
33 std::conditional_t<N <= std::numeric_limits<uint8_t >::max(), uint8_t,
34 std::conditional_t<N <= std::numeric_limits<uint16_t>::max(), uint16_t,
35 std::conditional_t<N <= std::numeric_limits<uint32_t>::max(), uint32_t,
36 uint64_t>>>;
37
38public:
39 constexpr static_vector() = default;
40
41 explicit constexpr static_vector(std::initializer_list<T> list) {
42 assert(list.size() <= N);
43 std::copy(list.begin(), list.end(), data.data());
44 sz = SizeType(list.size());
45 }
46
47 template<typename Range>
48 constexpr static_vector(from_range_t, Range&& range) {
49 for (auto&& elem : range) {
50 push_back(elem);
51 }
52 }
53
54 [[nodiscard]] constexpr auto begin() const noexcept { return data.begin(); }
55 [[nodiscard]] constexpr auto end() const noexcept { return data.begin() + sz; }
56
57 [[nodiscard]] constexpr size_t size() const { return sz; }
58 [[nodiscard]] constexpr bool empty() const { return sz == 0; }
59
60 [[nodiscard]] constexpr T& operator[](size_t index) { return data[index]; }
61 [[nodiscard]] constexpr const T& operator[](size_t index) const { return data[index]; }
62
63 constexpr void push_back(const T& a) { assert(sz < N); data[sz++] = a; }
64
65 constexpr void clear() { sz = 0; }
66
67 operator std::span< T>() { return {data.data(), sz}; }
68 operator std::span<const T>() const { return {data.data(), sz}; }
69
70private:
71 std::array<T, N> data = {};
72 SizeType sz = 0;
73};
74
75#endif
constexpr void clear()
constexpr auto begin() const noexcept
constexpr T & operator[](size_t index)
constexpr static_vector(from_range_t, Range &&range)
constexpr static_vector(std::initializer_list< T > list)
constexpr const T & operator[](size_t index) const
constexpr static_vector()=default
constexpr auto end() const noexcept
constexpr size_t size() const
constexpr bool empty() const
constexpr void push_back(const T &a)
constexpr from_range_t from_range