As a result for example std::optional<&T> doesn't exist, because to a C++ programmer it seems as though this might have assign-through semantics (!) and so WG21 decided to kick this can down the road. C++ 26 might get std::optional<&T>
As a result for example std::optional<&T> doesn't exist, because to a C++ programmer it seems as though this might have assign-through semantics (!) and so WG21 decided to kick this can down the road. C++ 26 might get std::optional<&T>
The main concern with that component was ensuring we can allocate stack storage for an object that may or may not be initialized.
The reference is easily achievable by using T* so is of minimal value, but also poses some more semantic problems since a reference is not copyable while an optional is.
For me the important use case is pattern matching, which C++ doesn't yet have. Pattern matching really changes how you see the entire language.
Here is the first example I found on Google if that helps you understand.
std::variant<Fluid, LightItem, HeavyItem, FragileItem> package;
std::visit(overload{
[](Fluid& ) { std::cout << "fluid\n"; },
[](LightItem& ) { std::cout << "light item\n"; },
[](HeavyItem& ) { std::cout << "heavy item\n"; },
[](FragileItem& ) { std::cout << "fragile\n"; }
}, package); match (state, pipe) {
(State::None, Pipe::Ground) => {
if inside {
n += 1;
}
}
(State::None, Pipe::Vert) => {
inside = !inside;
}
(State::None, Pipe::Se) => {
state = State::South;
}
(State::None, Pipe::Ne) => {
state = State::North;
}
// Horizontal lines make no difference to anything
(State::North | State::South, Pipe::Horiz) => {}
// U-turns
(State::South, Pipe::Sw) | (State::North, Pipe::Nw) => {
state = State::None;
}
// Form a vertical line
(State::South, Pipe::Nw) | (State::North, Pipe::Sw) => {
inside = !inside;
state = State::None;
}
_ => {
panic!("Unexpected sequence {state:?} {pipe:?}");
}
}Guess what, the same syntax I gave supports exactly that as well.