c++pass-by-referenceauto-ptr

What is the danger of passing an auto_ptr to a function expecting a constant reference to an auto_ptr?


Nicolai Josuttis, in his book "The C++ Standard Library - A Tutorial and Reference", writes, at page 44, the following paragraph :

According to the concept of auto_ptrs, it is possible to transfer ownership into a function by using a constant reference. This is very dangerous because people usually expect that an object won't get modified when you pass it as a constant reference. Fortunately, there was a late design decision that made auto_ptrs less dangerous. By some tricky implementation techniques, transfer of ownership is not possible with constant references. In fact, you can't change the ownership of any constant auto_ptr: …

If is not possible to change ownership with a constant reference, why the expressions "This is very dangerous" and "less dangerous" above ?


Solution

  • Summing up comments:

    "This is very dangerous" refers to when std::auto_ptr<>'s copy constructor (which transfers ownership) took a const reference argument – this is a complete violation of const-correctness.

    "Less dangerous" refers to the fact that the copy constructor (which now takes a non-const reference) can transfer ownership at all; this is still dangerous, just not as dangerous as when the copy constructor took a const reference.

    This aspect of std::auto_ptr<> is universally considered a flaw in the class, to the extent that it's generally considered unusably broken. Consequently, boost::scoped_ptr<> and boost::shared_ptr<> are largely considered the "real" smart pointers of C++03, and in C++11 std::auto_ptr<> is deprecated altogether in favor of std::unique_ptr<> (and removed entirely in C++17).


    Update: As of Boost 1.57, the Boost.Move library now supplies a C++03 emulation of std::unique_ptr<> which should be used rather than boost::scoped_ptr<>: boost::movelib::unique_ptr<>.