11#include <memory_resource>
13#include "../utility/utility.hpp"
14#include "../macros.hpp"
35 static_assert(not std::is_reference_v<value_type>);
36 static_assert(not std::is_const_v<value_type>);
42 return generator{handle_type::from_promise(*
this)};
45 value_type
const& value()
const noexcept
51 static std::suspend_never initial_suspend()
noexcept
56 static std::suspend_always final_suspend()
noexcept
61 std::suspend_always yield_value(value_type
const& value)
noexcept
67 std::suspend_always yield_value(value_type&& value)
noexcept
73 void return_void()
noexcept {}
76 void await_transform() =
delete;
78 void unhandled_exception()
noexcept
85 if (
auto ptr = std::exchange(_exception,
nullptr)) {
91 std::optional<value_type> _value = {};
95 using handle_type = std::coroutine_handle<promise_type>;
99 value_proxy(value_type
const& value) noexcept : _value(value) {}
101 value_type
const& operator*()
const noexcept
114 using difference_type = ptrdiff_t;
115 using value_type = std::decay_t<value_type>;
116 using pointer = value_type
const *;
117 using reference = value_type
const&;
120 explicit const_iterator(handle_type coroutine) : _coroutine{coroutine} {}
126 hi_axiom(not at_end());
128 _coroutine.promise().rethrow();
134 auto tmp =
value_proxy(_coroutine.promise().value());
135 hi_axiom(not at_end());
137 _coroutine.promise().rethrow();
143 decltype(
auto)
operator*()
const
145 hi_axiom(not at_end());
146 return _coroutine.promise().value();
149 pointer *operator->() const noexcept
151 hi_axiom(not at_end());
155 [[nodiscard]]
bool at_end() const noexcept
157 return not _coroutine or _coroutine.done();
162 [[nodiscard]]
bool operator==(std::default_sentinel_t)
const noexcept
168 handle_type _coroutine;
171 explicit generator(handle_type coroutine) : _coroutine(coroutine) {}
173 generator() =
default;
177 _coroutine.destroy();
181 generator(
const generator&) =
delete;
182 generator& operator=(
const generator&) =
delete;
184 generator(generator&& other) noexcept : _coroutine{std::exchange(
other._coroutine, {})} {}
186 generator& operator=(generator&& other)
noexcept
188 hi_return_on_self_assignment(other);
190 _coroutine.destroy();
192 _coroutine = std::exchange(
other._coroutine, {});
212 std::default_sentinel_t
end()
const
219 std::default_sentinel_t
cend()
const
225 handle_type _coroutine;
231 using value_type = T&;
237 return generator{handle_type::from_promise(*
this)};
240 value_type value()
const noexcept
242 hi_axiom(_value !=
nullptr);
247 static std::suspend_never initial_suspend()
noexcept
252 static std::suspend_always final_suspend()
noexcept
257 std::suspend_always yield_value(value_type value)
noexcept
263 void return_void()
noexcept {}
266 void await_transform() =
delete;
268 void unhandled_exception()
noexcept
275 if (
auto ptr = std::exchange(_exception,
nullptr)) {
281 std::remove_reference_t<value_type> *_value =
nullptr;
285 using handle_type = std::coroutine_handle<promise_type>;
289 value_proxy(value_type value) noexcept : _value(
std::addressof(value)) {}
291 value_type operator*()
const noexcept
297 std::remove_reference_t<value_type> *_value;
302 class const_iterator {
304 using difference_type = ptrdiff_t;
305 using value_type = std::decay_t<value_type>;
306 using pointer = value_type
const *;
307 using reference = value_type
const&;
310 explicit const_iterator(handle_type coroutine) : _coroutine{coroutine} {}
316 hi_axiom(not at_end());
318 _coroutine.promise().rethrow();
322 value_proxy operator++(
int)
324 auto tmp = value_proxy(_coroutine.promise().value());
325 hi_axiom(not at_end());
327 _coroutine.promise().rethrow();
333 decltype(
auto)
operator*()
const
335 hi_axiom(not at_end());
336 return _coroutine.promise().value();
339 pointer *operator->() const noexcept
341 hi_axiom(not at_end());
345 [[nodiscard]]
bool at_end() const noexcept
347 return not _coroutine or _coroutine.done();
352 [[nodiscard]]
bool operator==(std::default_sentinel_t)
const noexcept
358 handle_type _coroutine;
363 generator() =
default;
367 _coroutine.destroy();
371 generator(
const generator&) =
delete;
372 generator& operator=(
const generator&) =
delete;
374 generator(generator&& other)
noexcept : _coroutine{std::exchange(
other._coroutine, {})} {}
376 generator& operator=(generator&& other)
noexcept
378 hi_return_on_self_assignment(other);
380 _coroutine.destroy();
382 _coroutine = std::exchange(
other._coroutine, {});
390 return const_iterator{_coroutine};
397 return const_iterator{_coroutine};
402 std::default_sentinel_t
end()
const
409 std::default_sentinel_t
cend()
const
415 handle_type _coroutine;
@ other
The gui_event does not have associated data.
DOXYGEN BUG.
Definition algorithm.hpp:16
constexpr Out narrow_cast(In const &rhs) noexcept
Cast numeric values without loss of precision.
Definition cast.hpp:377
A return value for a generator-function.
Definition generator.hpp:31
std::default_sentinel_t end() const
Return a sentinel for the iterator.
Definition generator.hpp:212
const_iterator cbegin() const
Start the generator-function and return an iterator.
Definition generator.hpp:205
std::default_sentinel_t cend() const
Return a sentinel for the iterator.
Definition generator.hpp:219
const_iterator begin() const
Start the generator-function and return an iterator.
Definition generator.hpp:198
Definition generator.hpp:38
Definition generator.hpp:97
A forward iterator which iterates through values co_yieled by the generator-function.
Definition generator.hpp:112
const_iterator & operator++()
Resume the generator-function.
Definition generator.hpp:124
bool operator==(std::default_sentinel_t) const noexcept
Check if the generator-function has finished.
Definition generator.hpp:162
std::default_sentinel_t cend() const
Return a sentinel for the iterator.
Definition generator.hpp:409
std::default_sentinel_t end() const
Return a sentinel for the iterator.
Definition generator.hpp:402
const_iterator begin() const
Start the generator-function and return an iterator.
Definition generator.hpp:388
const_iterator cbegin() const
Start the generator-function and return an iterator.
Definition generator.hpp:395
bool operator==(std::default_sentinel_t) const noexcept
Check if the generator-function has finished.
Definition generator.hpp:352
const_iterator & operator++()
Resume the generator-function.
Definition generator.hpp:314
T current_exception(T... args)
T rethrow_exception(T... args)