1#ifndef NEFORCE_CORE_ASYNC_GENERATOR_HPP__
2#define NEFORCE_CORE_ASYNC_GENERATOR_HPP__
15#if defined(NEFORCE_STANDARD_20) || defined(NEXUSFORCE_ENABLE_DOXYGEN)
19NEFORCE_BEGIN_NAMESPACE__
63 NEFORCE_THROW_EXCEPTION(
exception(
"Operation cancelled"));
71 atomic<size_t> ref_count{1};
89 state_(new state()) {}
96 state_(other.state_) {
113 state_ = other.state_;
212 using value_type = T;
215 using reference = T&;
254 return *
handle.promise().current_value;
294 handle_(other.handle_) {
295 other.handle_ =
nullptr;
311 handle_ = other.handle_;
312 other.handle_ =
nullptr;
336 if (handle_.promise().exception) {
339 if (handle_.done()) {
358 template <
typename F>
360 for (
auto&& value: *
this) {
361 co_yield func(_NEFORCE
forward<
decltype(value)>(value));
371 template <
typename Pred>
373 for (
auto&& value: *
this) {
387 for (
auto&& value: *
this) {
403 for (
auto&& value: *
this) {
418 for (
auto&& value: *
this) {
421 for (
auto&& value: other) {
431 template <
typename F>
433 for (
auto&& value: *
this) {
434 func(_NEFORCE
forward<
decltype(value)>(value));
446 template <
typename Acc,
typename F>
448 Acc result = _NEFORCE
move(init);
449 for (
auto&& value: *
this) {
450 result = func(_NEFORCE
move(result), _NEFORCE
forward<
decltype(value)>(value));
569 handle.promise().continuation = continuation;
578 if (
handle.promise().exception) {
581 return _NEFORCE
move(*
handle.promise().result);
601 handle_(other.handle_) {
602 other.handle_ =
nullptr;
618 handle_ = other.handle_;
619 other.handle_ =
nullptr;
646 bool done() const noexcept {
return handle_.done(); }
652 if (handle_ && !handle_.done()) {
662 while (!handle_.done()) {
665 if (handle_.promise().exception) {
668 return _NEFORCE
move(*handle_.promise().result);
677 handle_.promise().set_cancellation_token(&token);
685 bool is_cancelled() const noexcept {
return handle_ && handle_.promise().is_cancelled(); }
695 struct promise_type {
708 struct final_awaiter {
724 void return_void()
noexcept {}
735 handle.promise().continuation = continuation;
740 if (
handle.promise().exception) {
753 task(task&& other) noexcept :
754 handle_(other.handle_) {
755 other.handle_ =
nullptr;
766 handle_ = other.handle_;
767 other.handle_ =
nullptr;
778 task(
const task&) =
delete;
781 awaiter
operator co_await() {
return awaiter{handle_}; }
783 bool done()
const {
return handle_.
done(); }
786 if (handle_ && !handle_.done()) {
792 while (!handle_.done()) {
795 if (handle_.promise().exception) {
802 handle_.promise().set_cancellation_token(&token);
806 bool is_cancelled()
const {
return handle_ && handle_.promise().is_cancelled(); }
813template <
typename... Ts>
814struct when_all_result {
818template <
size_t I,
typename Tuple,
typename... Tasks,
enable_if_t<(I <
sizeof...(Tasks)),
int> = 0>
819task<void> when_all_helper(Tuple& results, Tasks&&... tasks) {
821 _NEFORCE
get<I>(results) =
co_await _NEFORCE
move(current_task);
822 co_await when_all_helper<I + 1>(results, _NEFORCE
forward<Tasks>(tasks)...);
826template <
size_t I,
typename Tuple,
typename... Tasks,
enable_if_t<I ==
sizeof...(Tasks),
int> = 0>
827task<void> when_all_helper(Tuple&, Tasks&&...) {
842template <
typename... Tasks>
843auto when_all(Tasks&&... tasks) ->
task<tuple<
typename Tasks::promise_type::result_type...>> {
844 tuple<
typename Tasks::promise_type::result_type...> results;
845 co_await inner::when_all_helper<0>(results, _NEFORCE
forward<Tasks>(tasks)...);
861template <
typename T,
typename Factory>
868 for (
size_t attempt = 0; attempt < max_attempts; ++attempt) {
870 co_return co_await factory();
874 if (should_retry && !should_retry(last_exception)) {
877 if (attempt == max_attempts - 1) {
888NEFORCE_END_NAMESPACE__
void cancel() noexcept
请求取消
check_awaiter check() const
获取取消检查等待器
~cancellation_token()
析构函数,释放状态
cancellation_token & operator=(const cancellation_token &other)
拷贝赋值运算符
bool is_cancelled() const noexcept
检查是否已被取消
cancellation_token()
默认构造函数,创建新的取消令牌
cancellation_token(const cancellation_token &other)
拷贝构造函数,共享状态
generator(coroutine_handle< promise_type > h)
从协程句柄构造
generator skip(const size_t n)
跳过前n个元素
generator take(const size_t n)
取前n个元素
generator chain(generator &&other)
连接两个生成器
generator & operator=(generator &&other) noexcept
移动赋值运算符
invoke_result_t< F, T > map(F &&func)
映射变换
void for_each(F &&func)
遍历每个元素
generator(generator &&other) noexcept
移动构造函数
Acc fold(Acc init, F &&func)
折叠(归约)
generator filter(Pred &&pred)
过滤
void set_cancellation_token(cancellation_token &token)
设置取消令牌
task & operator=(task &&other) noexcept
移动赋值运算符
task(task &&other) noexcept
移动构造函数
bool done() const noexcept
检查任务是否已完成
bool is_cancelled() const noexcept
检查任务是否被取消
task(coroutine_handle< promise_type > h)
从协程句柄构造
NEFORCE_NODISCARD constexpr T * addressof(T &x) noexcept
获取对象的地址
NEFORCE_NODISCARD constexpr T && forward(remove_reference_t< T > &x) noexcept
完美转发左值
NEFORCE_ALWAYS_INLINE enable_if_t< is_void_v< T >, future_result_t< T > > get(future< T > &f)
通用future结果获取函数
noop_coroutine_handle noop_coroutine() noexcept
获取空操作协程句柄
std::coroutine_handle< Promise > coroutine_handle
协程句柄
task< T > retry(Factory &&factory, const size_t max_attempts, function< bool(const exception_ptr &)> should_retry=nullptr)
带重试的异步操作
auto when_all(Tasks &&... tasks) -> task< tuple< typename Tasks::promise_type::result_type... > >
等待所有任务完成
constexpr iter_difference_t< Iterator > count(Iterator first, Iterator last, const T &value)
统计范围内等于指定值的元素数量
#define NEFORCE_CONSTEXPR_ASSERT(COND)
编译时常量断言
void NEFORCE_API rethrow_exception(const exception_ptr &p)
重新抛出异常
exception_ptr NEFORCE_API current_exception() noexcept
获取当前异常
NEFORCE_INLINE17 constexpr bool is_invocable_r_v
is_invocable_r的便捷变量模板
typename inner::__invoke_result_aux< F, Args... >::type invoke_result_t
invoke_result的便捷别名
NEFORCE_INLINE17 constexpr auto memory_order_acq_rel
获取-释放内存顺序常量
NEFORCE_INLINE17 constexpr auto memory_order_release
释放内存顺序常量
NEFORCE_INLINE17 constexpr auto memory_order_relaxed
宽松内存顺序常量
NEFORCE_INLINE17 constexpr auto memory_order_acquire
获取内存顺序常量
constexpr Iterator2 move(Iterator1 first, Iterator1 last, Iterator2 result) noexcept(noexcept(inner::__move_aux(first, last, result)))
移动范围元素
NEFORCE_ALWAYS_INLINE_INLINE thread::native_handle_type handle() noexcept
获取当前线程句柄
NEFORCE_NODISCARD constexpr tuple< Types &&... > forward_as_tuple(Types &&... args) noexcept
创建转发引用元组
typename enable_if< Test, T >::type enable_if_t
enable_if的便捷别名
bool await_ready() const noexcept
检查是否可立即恢复
const cancellation_token * token
令牌指针
void await_resume() const
恢复时执行的操作
void await_suspend(coroutine_handle<> h) const noexcept
暂停协程(实际上从不暂停)
T & operator*() const noexcept
解引用,获取当前值
bool operator!=(const iterator &other) const noexcept
不等比较
bool operator==(const iterator &other) const noexcept
相等比较
coroutine_handle< promise_type > handle
协程句柄
iterator(coroutine_handle< promise_type > h)
从协程句柄构造
T * operator->() const noexcept
箭头操作符
iterator & operator++()
前置递增,恢复协程获取下一个值
optional< T > current_value
当前产生的值
void return_void() noexcept
返回void(生成器不返回值)
suspend_always yield_value(T value)
产生一个值
exception_ptr exception
异常指针
void unhandled_exception()
处理未捕获的异常
suspend_always final_suspend() noexcept
最终暂停点
suspend_always initial_suspend() noexcept
初始暂停点
generator get_return_object()
获取生成器对象
coroutine_handle< promise_type > handle
协程句柄
bool await_ready() const noexcept
检查是否可立即恢复
coroutine_handle await_suspend(coroutine_handle<> continuation) noexcept
暂停时执行的操作
void await_resume() noexcept
恢复时执行的操作
bool await_ready() noexcept
检查是否可立即恢复
coroutine_handle await_suspend(coroutine_handle< promise_type > h) noexcept
暂停时执行的操作
void unhandled_exception() noexcept
处理未捕获的异常
void return_value(T value)
设置返回值
void set_cancellation_token(cancellation_token *t) noexcept
设置取消令牌
final_awaiter final_suspend() noexcept
最终暂停点
cancellation_token * token
取消令牌
task get_return_object()
获取任务对象
coroutine_handle continuation
继续执行的协程
bool is_cancelled() const noexcept
检查是否已取消
suspend_always initial_suspend() noexcept
初始暂停点
exception_ptr exception
异常指针