On Wed, Oct 2, 2013 at 4:18 AM, Luke Bradford
Thanks for the feedback, Matt - some quick thoughts:
Not having a default constructor seems unnecessary to me. Why not just have the default constructor dynamically allocate a default constructed object? Similarly, for consistency with other smart pointers, having a conversion to bool would be useful and makes transition to the type simpler.
Often the object pointed to will not have a default constructor, so we wouldn't be able to construct one in shared_ptr_nonnull's default constructor.
This does not prevent your template from having a default constructor in the case that the type has a default constructor. I only consider this very useful because there are plenty of times where generic code takes advantage of default constructability. For example, resizing a container without an explicit value.
I also think that having a conversion to bool is misleading - in the use cases I've seen, it would lead to a lot of extraneous if( ptr ) statements, then essentially if( true ), which obscure the programmer's intentions and are easy to remove. I found the elimination of the default constructor and conversion to bool just as useful, if not more useful, than the runtime checks of the class, because they revealed places where we were default constructing or checking a shared_ptr that we expected to be valid at all times.
The point isn't for people to use them in new code written specifically for the type, it's both to transition from old code and to work fine with generic code. You can also think of it as how boost::variant has an "empty" function that just always returns false.
I like the implicit conversion for convenience in using the class in place of shared_ptr. Is there a reason you wouldn't want to have implicit conversion?
For all of the standard reasons that implicit conversion is to generally be avoided, which I won't spend time repeating here. -- -Matt Calabrese