Hasan Zeen
Hasan Zeen

Reputation: 157

Is move() with unique_ptr irreplaceable?

I am not sure if the title is even relative as I do not have enough knowledge about move(). For this very reason it was hard to search and successfully find an answer to my question.

consider the following code:

using namespace std;

struct A
{
    A(){cout << "Created!\n";}
    ~A(){cout << "Destroyed!\n";};
};

void f()
{
    unique_ptr<A> q(new A);

    unique_ptr<A> t (q.release());  // ----> (1)
    // unique_ptr<A> t = move(q);   // ----> (2) 
}

int main() { f(); }

My understanding is: in both cases (1) and (2) the t will take the A ownership from q without destroying the object A.

  1. Is this correct?
  2. What is the difference between (1) and (2)?

I can see that move() is not part of the unique_ptr, instead it seems to me part of std so it has more general uses.

I am new to C++ and so in the simplest possible way:

  1. What can move do? What are its uses?

Upvotes: 3

Views: 91

Answers (1)

rodrigo
rodrigo

Reputation: 98516

  1. Yes, it is correct.
  2. In your case, no visible difference.

Let me elaborate on question 3: what can move do?

std::move, as you noted, is not part of unique_ptr but of std. It is able to move any moveable object, not just pointers.

In the particular case of unique_ptr there is that handy release() that allows you to move the pointer manually, without using the move operators. But think for example of std::thread or std::fstream, there are no release/reacquire operators there.

Note that std::move by itself does nothing. Some people think that it returns a temporary while destroying the original, so a single:

std::unique_ptr<A> q(new A);
std::move(q); //this does nothing!!!

would move q to nothingness and destroy the object...

This is not true. All that std::move() does is a cast to an rvalue-reference. It is actually the move assignment operator (operator=(T&&)) or the move constructor (T(T&&)) that does the real moving.

You could also say:

std::unique_ptr<A> q(new A);
std::unique_ptr<A> r(static_cast<std::unique_ptr<A>&&>(q));

but that is cumbersome. std::move() is nicer to look at:

std::unique_ptr<A> q(new A);
std::unique_ptr<A> r(std::move(q));

Upvotes: 4

Related Questions