emlabcpp
modern opinionated embedded C++ library
iterator.h
Go to the documentation of this file.
1 
24 #pragma once
25 
26 #include <iterator>
27 
28 namespace emlabcpp
29 {
30 
31 template < typename Derived >
32 concept nothrow_dereference = requires( Derived d ) {
33  { *d } noexcept;
34 };
35 
36 template < typename Derived >
37 concept nothrow_add_assign = requires( Derived d ) {
38  { d += 1 } noexcept;
39 };
40 
41 template < typename Derived >
42 concept nothrow_sub_assign = requires( Derived d ) {
43  { d -= 1 } noexcept;
44 };
45 
46 template < typename Derived >
47 concept nothrow_threeway_compare = requires( Derived d ) {
48  { d <=> d } noexcept;
49 };
50 
51 template < typename Derived >
52 concept nothrow_equality_compare = requires( Derived d ) {
53  { d == d } noexcept;
54 };
55 
60 
61 template < typename Derived >
63 
64 template < typename Derived >
66 {
67  [[nodiscard]] constexpr Derived& impl() noexcept
68  {
69  return static_cast< Derived& >( *this );
70  }
71 
72  [[nodiscard]] constexpr Derived const& impl() const noexcept
73  {
74  return static_cast< Derived const& >( *this );
75  }
76 
77  generic_iterator_base() noexcept = default;
78  friend Derived;
80 
81 public:
85  using iterator_category = typename std::iterator_traits< Derived >::iterator_category;
87  using const_reference = reference const;
88  using difference_type = typename std::iterator_traits< Derived >::difference_type;
89 
90  constexpr pointer operator->() noexcept( nothrow_dereference< Derived > )
91  {
92  return &*impl();
93  }
94 
95  constexpr const_pointer operator->() const noexcept( nothrow_dereference< Derived > )
96  {
97  return &*impl();
98  }
99 };
100 
101 template < typename Derived >
102 requires( std::same_as<
103  typename std::iterator_traits< Derived >::iterator_category,
104  std::random_access_iterator_tag > )
105 struct generic_iterator< Derived > : public generic_iterator_base< Derived >
106 {
107  using generic_iterator_base< Derived >::impl;
108 
109  using difference_type = typename std::iterator_traits< Derived >::difference_type;
110 
111  constexpr Derived& operator++() noexcept( nothrow_add_assign< Derived > )
112  {
113  impl() += 1;
114  return impl();
115  }
116 
117  constexpr Derived operator++( int const ) noexcept(
118  nothrow_add_assign< Derived > && std::is_nothrow_copy_constructible_v< Derived > )
119  {
120  auto copy = impl();
121  impl() += 1;
122  return copy;
123  }
124 
125  constexpr Derived& operator--() noexcept( nothrow_sub_assign< Derived > )
126  {
127  impl() -= 1;
128  return impl();
129  }
130 
131  constexpr Derived operator--( int const ) noexcept(
132  nothrow_sub_assign< Derived > && std::is_nothrow_copy_constructible_v< Derived > )
133  {
134  auto copy = impl();
135  impl() -= 1;
136  return copy;
137  }
138 
139  constexpr Derived operator+( difference_type v ) const noexcept(
140  nothrow_add_assign< Derived > && std::is_nothrow_copy_constructible_v< Derived > )
141  {
142  auto copy = impl();
143  copy += v;
144  return copy;
145  }
146 
147  constexpr Derived operator-( difference_type v ) const noexcept(
148  nothrow_sub_assign< Derived > && std::is_nothrow_copy_constructible_v< Derived > )
149  {
150  auto copy = impl();
151  copy -= v;
152  return copy;
153  }
154 };
155 
156 template < typename Derived >
157 requires( std::same_as<
158  typename std::iterator_traits< Derived >::iterator_category,
159  std::bidirectional_iterator_tag > )
160 struct generic_iterator< Derived > : public generic_iterator_base< Derived >
161 {
162  using generic_iterator_base< Derived >::impl;
163 
164  constexpr Derived operator++( int const ) noexcept(
165  nothrow_add_assign< Derived > && std::is_nothrow_copy_constructible_v< Derived > )
166  {
167  auto copy = impl();
168  ++impl();
169  return copy;
170  }
171 
172  constexpr Derived operator--( int const ) noexcept(
173  nothrow_sub_assign< Derived > && std::is_nothrow_copy_constructible_v< Derived > )
174  {
175  auto copy = impl();
176  --impl();
177  return copy;
178  }
179 };
180 
181 template < typename Derived >
182 requires( std::same_as<
183  typename std::iterator_traits< Derived >::iterator_category,
184  std::input_iterator_tag > )
185 struct generic_iterator< Derived > : public generic_iterator_base< Derived >
186 {
187  using generic_iterator_base< Derived >::impl;
188 
189  constexpr Derived operator++( int const ) noexcept(
190  nothrow_add_assign< Derived > && std::is_nothrow_copy_constructible_v< Derived > )
191  {
192  auto copy = impl();
193  ++impl();
194  return copy;
195  }
196 };
197 
198 } // namespace emlabcpp
Definition: iterator.h:66
reference const const_reference
Definition: iterator.h:87
constexpr pointer operator->() noexcept(nothrow_dereference< Derived >)
Definition: iterator.h:90
typename std::iterator_traits< Derived >::pointer pointer
Definition: iterator.h:83
typename std::iterator_traits< Derived >::value_type value_type
Definition: iterator.h:82
typename std::iterator_traits< Derived >::iterator_category iterator_category
Definition: iterator.h:85
typename std::iterator_traits< Derived >::const_pointer const_pointer
Definition: iterator.h:84
typename std::iterator_traits< Derived >::reference reference
Definition: iterator.h:86
constexpr const_pointer operator->() const noexcept(nothrow_dereference< Derived >)
Definition: iterator.h:95
typename std::iterator_traits< Derived >::difference_type difference_type
Definition: iterator.h:88
std::variant< int64_t, float, bool, string_buffer > value_type
Definition: base.h:51
MIT License.
Definition: impl.h:31
concept nothrow_dereference
Definition: iterator.h:32
constexpr point< N > operator+(point< N > a, vector< N > const &b)
Returns a result of addition a to b, viz += operator.
Definition: point.h:93
T const * const_pointer
Definition: static_storage.h:104
T & reference
Definition: static_storage.h:101
void copy(Container &&cont, Iterator iter)
Definition: algorithm.h:455
T * pointer
Definition: static_storage.h:103
concept nothrow_equality_compare
Definition: iterator.h:52
concept nothrow_sub_assign
Definition: iterator.h:42
concept nothrow_threeway_compare
Definition: iterator.h:47
requires(!range_container< Container >) const expr std
Returns index of an element in tuple 't', for which call to predicate f(x) holds true,...
Definition: algorithm.h:127
constexpr vector< N > operator-(point< N > a, point< N > const &b)
Returns a result of subtraction of A from B, viz -= operator.
Definition: point.h:84
concept nothrow_add_assign
Definition: iterator.h:37
generic_iterator simplifies custom iterator implementation using CRTP.
Definition: iterator.h:62