C++20coreadvanced
Coroutines (C++20 Addition)
C++20 · The Big Four · Compiler flag: -std=c++20
Explanation
Functions that can suspend and resume execution, enabling asynchronous programming.
Real-World Scenario
Implement a non-blocking task scheduler in a server application.
Quick Snippet
snippet.cpp
#include <coroutine> std::suspend_always yield() { return {}; }Full Example
coroutines.cpp
// CodeNebula - C++20 Example: Coroutines Overview
// Compile: g++ -std=c++20 -Wall -Wextra -o example coroutines.cpp
// C++20 coroutines introduce three new keywords:
// co_await — suspend and wait for a result
// co_yield — suspend and produce a value
// co_return — complete the coroutine with a final value
// A function becomes a coroutine if its body uses any of these keywords.
#include <iostream>
#include <coroutine>
// --- A simple Generator coroutine type ---
// Demonstrates co_yield: produces a sequence of values lazily.
struct Generator {
struct promise_type {
int current_value;
Generator get_return_object() {
return Generator{std::coroutine_handle<promise_type>::from_promise(*this)};
}
std::suspend_always initial_suspend() { return {}; }
std::suspend_always final_suspend() noexcept { return {}; }
std::suspend_always yield_value(int value) {
current_value = value;
return {};
}
void return_void() {}
void unhandled_exception() { std::terminate(); }
};
std::coroutine_handle<promise_type> handle;
explicit Generator(std::coroutine_handle<promise_type> h) : handle(h) {}
~Generator() { if (handle) handle.destroy(); }
// Non-copyable, movable
Generator(const Generator&) = delete;
Generator& operator=(const Generator&) = delete;
Generator(Generator&& o) noexcept : handle(o.handle) { o.handle = nullptr; }
bool next() {
handle.resume();
return !handle.done();
}
int value() const { return handle.promise().current_value; }
};
// A coroutine function using co_yield
Generator count_up_to(int limit) {
for (int i = 1; i <= limit; ++i) {
co_yield i; // suspend, produce a value
}
// implicit co_return (return_void)
}
// A coroutine using co_yield for Fibonacci numbers
Generator fibonacci(int count) {
int a = 0, b = 1;
for (int i = 0; i < count; ++i) {
co_yield a;
int next = a + b;
a = b;
b = next;
}
}
int main() {
std::cout << "=== C++20 Coroutines Overview ===\n\n";
// co_yield example: counting
std::cout << "count_up_to(5): ";
auto counter = count_up_to(5);
while (counter.next()) {
std::cout << counter.value() << " ";
}
std::cout << "\n";
// co_yield example: fibonacci
std::cout << "fibonacci(8): ";
auto fib = fibonacci(8);
while (fib.next()) {
std::cout << fib.value() << " ";
}
std::cout << "\n";
std::cout << "\nCoroutine keywords:\n";
std::cout << " co_yield - suspend and produce a value\n";
std::cout << " co_await - suspend and wait for a result\n";
std::cout << " co_return - finish with a final value\n";
return 0;
}
// Expected output:
// === C++20 Coroutines Overview ===
//
// count_up_to(5): 1 2 3 4 5
// fibonacci(8): 0 1 1 2 3 5 8 13
//
// Coroutine keywords:
// co_yield - suspend and produce a value
// co_await - suspend and wait for a result
// co_return - finish with a final value
Run command
g++ -std=c++20 -Wall -Wextra -o example coroutines.cpp