26

C++11's std::shared_ptr<> provides a kind of bool operator.

operator unspecified-bool-type() const;

(It's not a straight-up operator bool() const due to the dangers from implicit casting of type bool.)

Why doesn't std::weak_ptr<> have a similar operator? I find myself constantly typing

if( !wp.expired() )

when I want to type

if( wp )

Why no bool conversion for weak_ptr?

ildjarn
  • 62,044
  • 9
  • 127
  • 211
OldPeculier
  • 11,049
  • 13
  • 50
  • 76

1 Answers1

33

if(!wp.expired()) is almost always a wrong check in multithreaded code, because directly after that if statement the pointer could expire. As such, if weak_ptr had exactly that as the semantics for the bool conversion, it would never be used anyways.

If you want to check if the pointer is alive, use lock and check the obtained shared_ptr.

If you want to know if the pointer is dead, use expired.

As you can see, it just doesn't make sense to provide a boolean conversion. For shared_ptr, it totally does. Btw, the conversion operator is explicit operator bool() const noexcept; in C++11.

Xeo
  • 129,499
  • 52
  • 291
  • 397
  • 2
    "*If you want to check if the pointer is alive, use lock and check the obtained shared_ptr.*" Dangerous because you might wind up discarding the last strong pointer to the object, so you could only do this in a context in which it was safe to invoke the object's destructor. – David Schwartz Apr 09 '16 at 23:11
  • 5
    I would suggest that any context is safe to invoke any object's destructor, because destructors should be written in such a way that they may be safely called at any time (AIUI, this needs to be the case for exception handling to work in the general case, as stack unwinding could destruct any arbitrary object). I'd be interested in a counterexample though. – Keiji May 31 '16 at 16:03
  • Well, there are objects, whose destructor might throw or cause unwanted side effects. But such objects should never be wrapped inside a `shared_ptr` in the first place. – Kai Petzke Jun 24 '19 at 23:28
  • 5
    _it just doesn't make sense to provide a boolean conversion_: I disagree. If I want to check if the `weak_ptr` is empty, e.g. default constructed, the proper semantic is the one of `operator bool`. Using `expired` semantically implies that it was once valid. – lornova Sep 06 '19 at 07:37
  • This answer is overly opinionated and prescriptive. I wanted a simple bool conversion because I needed to add a sanity check assertion at a point in the program where the weak_ptr absolutely must be valid (enforces certain other preconditions). – sleep Oct 08 '22 at 10:45