'What is std::expected in C++?
In one of the most respected stackoverflow answer I found an example of std::expected
template class usages:
What are coroutines in C++20?
At the same time I cannot find any mentioning of this class on cppreference.com. Could you please explain what it is?
Solution 1:[1]
Actually, the best way to learn about std::expected
is a funny talk by the (in)famous Andrei Alexandrescu: "Expect the Expected!"
What it is and when it's used
Here are three complementing explanations of what an std::expected<T, E>
is:
It is the return type of a function which is supposed to return a
T
value - but which may encounter some error, in which case it will return a descriptor of that error, of typeE
.An example:
std::expected<ParsedData, ParsingError> parse_input(Input input);
It's an error-handling mechanism, being an alternative to throwing exceptions (in which case you always return the value you were supposed to), and to returning status/error codes (in which case you never return the value you want to, and have to use an out-parameter).
Here are the two alternative error-handling mechanisms applied to the function from the previous example:
ParsedData parse_input_2(Input input) noexcept(false); ParsingError parse_input_3(ParsedData& result, Input input);
It's discriminated union of types
T
andE
with some convenience methods.
"How is it better than just a std::variant<T,E>
?"
It behaves somewhat like std::optional<T>
, giving focus to the expected, rather than the unexpected, case:
result.has_value()
- true if we got a value rather than an error.if (result)
- checks for the same thing*result
- gives us theT
value if it exists, undefined behavior otherwise (same asstd::optional
, although many don't like this).result.value()
, gives us theT
value if it exists, or throws otherwise.
Actually, that last mode of access behaves differently than std::optional
if we got an error: What it throws is a bad_expected_access<E>
, with the returned error. This behavior can be thought of as a way to switch from expected-based to exception-based error-handling.
"Hey, I looked for it in the standard and it isn't there!"
std::expected
will be part of the upcoming C++23 standard. The proposal (P0323) has recently been accepted.
This being said - it is quite usable already, since it requires no new language facilities. I would recommend Sy Brand (tartanllama)'s implementation, which can be used with C++11 or later. It also has some neat functional-style extensions (which may not be standardized).
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
Solution | Source |
---|---|
Solution 1 |