Dispatch Queue
Dispatch Queue / Thread Pool implementation for C++11 with built-in C++20 coroutine support
 
Loading...
Searching...
No Matches
task.hpp
1#pragma once
2
3#ifdef __cpp_lib_coroutine
4#include <coroutine>
5#endif
6
7#include "function_result.hpp"
8#include "is_instance_of.hpp"
9#include "task_future.hpp"
10
11namespace dispatch_queue {
12
21template<typename T>
22class task {
23public:
24 using value_type = T;
25
26 task(std::shared_ptr<detail::task_future<T>> future)
27 : future(future)
28 {
29 }
30
31#ifdef __cpp_concepts
38 template<typename F>
40 auto then(F&& f) const {
41 auto nested_future = detail::task_future<detail::function_result<F, T>>::create_pending();
42 task value_this = *this;
43 future->then([=]() {
44 value_this.get().then([=](auto t) {
45 nested_future->do_work(f, t);
46 });
47 });
48 return to_task(nested_future);
49 }
50#endif
51
58 template<typename F>
59 auto then(F&& f) const {
60 task value_this = *this;
61 return to_task(future->then([=]() {
62 return f(value_this);
63 }));
64 }
65
71 T get() const {
72 return future->get();
73 }
74
78 task_state get_state() const {
79 return future->get_state();
80 }
81
85 std::exception_ptr get_exception() const {
86 return future->get_exception();
87 }
88
95 void wait() const {
96 future->wait();
97 }
98
107 template<class Rep, class Period>
108 bool wait_for(const std::chrono::duration<Rep, Period>& timeout_duration) const {
109 return future->wait_for(timeout_duration);
110 }
111
120 template<class Clock, class Duration>
121 bool wait_until(const std::chrono::time_point<Clock, Duration>& timeout_time) const {
122 return future->wait_until(timeout_time);
123 }
124
125#ifdef __cpp_lib_coroutine
126private:
127 class task_awaiter {
128 public:
129 task_awaiter(const task<T>& t) : t(t) {}
130 task_awaiter(task<T>&& t) : t(std::move(t)) {}
131
132 bool await_ready() const noexcept {
133 return t.get_state() != task_state::pending;
134 }
135
136 void await_suspend(std::coroutine_handle<> cont) const {
137 t.future->then([cont]{
138 cont();
139 if (cont.done()) {
140 cont.destroy();
141 }
142 });
143 }
144
145 T await_resume() {
146 return t.get();
147 }
148
149 private:
150 task<T> t;
151 };
152
153public:
165 task_awaiter operator co_await() const {
166 return task_awaiter(*this);
167 }
168#endif
169
170private:
171 std::shared_ptr<detail::task_future<T>> future;
172
174 template<typename U>
175 static task<U> to_task(std::shared_ptr<detail::task_future<U>> future) {
176 return task<U>(future);
177 }
178};
179
180} // end namespace dispatch_queue
Definition task_future.hpp:98
Definition task.hpp:22
bool wait_for(const std::chrono::duration< Rep, Period > &timeout_duration) const
Definition task.hpp:108
T get() const
Definition task.hpp:71
task_state get_state() const
Definition task.hpp:78
void wait() const
Definition task.hpp:95
std::exception_ptr get_exception() const
Definition task.hpp:85
bool wait_until(const std::chrono::time_point< Clock, Duration > &timeout_time) const
Definition task.hpp:121
auto then(F &&f) const
Definition task.hpp:59
Definition is_instance_of.hpp:10