For the case where rhs.has_value() is false and
this->has_value() is true, equivalent to:
if constexpr (is_nothrow_move_constructible_v<E>) {
E tmp(std::move(rhs.unex));
destroy_at(addressof(rhs.unex));
try {
construct_at(addressof(rhs.val), std::move(val));
destroy_at(addressof(val));
construct_at(addressof(unex), std::move(tmp));
} catch(...) {
construct_at(addressof(rhs.unex), std::move(tmp));
throw;
}
} else {
T tmp(std::move(val));
destroy_at(addressof(val));
try {
construct_at(addressof(unex), std::move(rhs.unex));
destroy_at(addressof(rhs.unex));
construct_at(addressof(rhs.val), std::move(tmp));
} catch (...) {
construct_at(addressof(val), std::move(tmp));
throw;
}
}
has_val = false;
rhs.has_val = true;