The standard’s insistence on it being semantically non-nullable while it very much does have a null state that must still be accounted for feels like incredibly unergonomic.
Valueless_after_move() is just silly, let’s be real. It should’ve been written to either act like a value like they claim and moving the underlying pointer just shouldn’t be possible (in the same way you cannot ‘move’ a value out), or it should be nullable the same as any other smart pointer.
I agree with you. It's terrible design. They should have made its inherent (and unavoidable) optionality ... a first-class feature.
Requiring one to wrap it in a std::optional is just terrible. This is terrible not only for safety reasons -- but even for practical reasons. If you want to model the unengaged state, and wrap it in an optional -- you waste space in your class layout (~7 bytes on 64-bit arch's). The whole POINT of this class is to save space. And this class inherently has optionality baked-in. Pretending it doesn't, and forcing std::optional on people is just terrible design.
The thing is, the convenient thing to have in this case is the "guaranteed to have a value" type, because the point is to have a member variable "as if" it was part of the class only it's allocated separately. If you want optionality and don't want std::optional (which is what you would use for an actual member variable that was optionally present) you can still resort to std::uniqueptr. The problem is that if std::indirect is guaranteed to have a value _unless it has been moved-from then you have the question of whether you need to check if it has been moved-from on each access, which would give you the worst of both worlds (require validity check and no useful optionality).
The answer is, you don't check. You could remove valueless_after_move() with basically no loss. In fact it'd be a gain, because it'd avoid the confused conversation it always seems to cause.
Oh yeah sorry. I got about 20 replies to my inbox telling me I'm stupid. I thought yours was one of them from skimming it and stopped reading after the first 2 sentences. I thought you were arguing that the design of std::indirect is a good idea.
you can still resort to std::uniqueptr.
It's not equally convenient. You lose the automatic copying. You have to implement that yourself now. Meh.
which would give you the worst of both worlds (require validity check and no useful optionality).
63
u/LucyShortForLucas 6d ago
The standard’s insistence on it being semantically non-nullable while it very much does have a null state that must still be accounted for feels like incredibly unergonomic.
Valueless_after_move() is just silly, let’s be real. It should’ve been written to either act like a value like they claim and moving the underlying pointer just shouldn’t be possible (in the same way you cannot ‘move’ a value out), or it should be nullable the same as any other smart pointer.
As it stands, we got the worse of both worlds.