co_return
- C++ course
- Advanced
- Lesson 69/83
- 5 min
Learn coroutine return with co_return.
What is co_return?
co_return finishes a coroutine and returns a value. It is used instead of normal return in coroutines. co_return v; calls the return_value(v) member of the promise.
For a valueless finish, co_return; (empty) is used; this calls return_void(). A coroutine either ends with co_return or reaches the end of its body. The return keyword cannot be used inside a coroutine; co_return is written instead.
promise_type::return_value
When a coroutine ends with co_return v;, the return_value(v) member of the promise is called. This member is used to store the return value.
Example: void return_value(int v) { value_ = v; }. Here the value is written into value_. After the coroutine finishes, you can read this value with handle.promise().value_. This way the result of the coroutine is read from outside in a type-safe way. If final_suspend returns suspend_always, the frame stays alive and the value can be read.
Practice Return a value with co_return
Write co_return 10; in the body of the compute coroutine. In main get the value with promise().value_ from the result of compute() and print it with std::cout.
Starter code
#include <iostream>
#include <coroutine>
struct Task {
struct promise_type {
int value_;
Task get_return_object() { return {std::coroutine_handle<promise_type>::from_promise(*this)}; }
std::suspend_never initial_suspend() { return {}; }
std::suspend_always final_suspend() noexcept { return {}; }
void return_value(int v) { value_ = v; }
void unhandled_exception() { }
};
std::coroutine_handle<promise_type> handle;
};
Task compute() {
// Return 10 with co_return
}
int main() {
// Call compute and print the value
return 0;
}Sample solution
#include <iostream>
#include <coroutine>
struct Task {
struct promise_type {
int value_;
Task get_return_object() { return {std::coroutine_handle<promise_type>::from_promise(*this)}; }
std::suspend_never initial_suspend() { return {}; }
std::suspend_always final_suspend() noexcept { return {}; }
void return_value(int v) { value_ = v; }
void unhandled_exception() { }
};
std::coroutine_handle<promise_type> handle;
};
Task compute() {
co_return 10;
}
int main() {
auto t = compute();
std::cout << t.handle.promise().value_;
return 0;
}Expected output
10
Questions and answers
Review the lesson questions together with their answers. To test yourself, solve the lesson interactively.
1 Match each expression to its role
| Term | Meaning |
|---|---|
co_return 42; |
Valued finish |
co_return; |
Valueless finish |
return_value |
Stores the value |
return_void |
Empty finish |
2 What is the difference between co_return and return?
- co_return is used inside a coroutine; return cannot be used Correct answer
- return is faster
- co_return only returns void
- There is no difference
Explanation: return cannot be used inside a coroutine; co_return is written instead.
3 the co_return expression
Task compute() { ____ 10; }
Task compute() { co_return 10; }
Explanation: co_return 10; finishes the coroutine and returns 10.