#include #include #include #include #include #include #include using namespace std; using namespace std::chrono; template struct Task { struct promise_type; using handle_type = std::coroutine_handle; struct promise_type { T value_; std::exception_ptr exception_; Task get_return_object() { return Task(handle_type::from_promise(*this)); } std::suspend_always initial_suspend() { return {}; } std::suspend_always final_suspend() noexcept { return {}; } void unhandled_exception() { exception_ = std::current_exception(); } template From> // C++20 concept void return_value(From &&from) { value_ = std::forward(from); } template From> // C++20 concept std::suspend_always yield_value(From &&from) { value_ = std::forward(from); return {}; } void return_void() {} }; handle_type h_; Task() { } Task(handle_type h) : h_(h) { } Task(const Task &t) : h_(t.h_) { } void destroy() { h_.destroy(); } T operator()() { assert(!h_.done()); call(); return std::move(h_.promise().value_); } bool done() { return h_.done(); } private: void call() { h_(); if (h_.promise().exception_) std::rethrow_exception(h_.promise().exception_); } }; #define pass() co_await std::suspend_always{} Task task_test() { pass(); for (unsigned i = 0; i < 3; ++i) co_yield i; co_return 1000; } int main() { const int task_count = 4; vector> tasks; for(int i = 0; i < task_count; i++) { auto t = task_test(); tasks.push_back(std::move(t)); } int done_count = 0; while(done_count < task_count) { for(int i = 0; i < task_count; i++) { Task &t = tasks[i]; if(t.done()) { t.destroy(); done_count++; } else { auto res = t(); cout << "T# " << i << " result " << res << endl; } } } }