Reputation: 207
Consider the following class prototype:
class ObjHandler {
std::unique_ptr<Obj> GetPtr() { return obj; }
private:
std::unique_ptr<Obj> obj;
};
This generates a compile-time error saying that the copy constructor of std::unique_ptr
is deleted. Why here move semantics are not applied? Is it related to the fact that GetPtr()
does not own the obj
pointer? How should I implement my code (I need a member function that returns an owning pointer to the stream with the minimum overhead)?
Upvotes: 5
Views: 1653
Reputation: 42868
Why here move semantics are not applied?
Because obj
is not a local variable, so the language doesn't allow it to be implicitly moved.
You can move it by using std::move
:
std::unique_ptr<Obj> GetPtr() { return std::move(obj); }
Although if this is really what you want, I'd recommend naming the function something that makes it clear that the ownership is being transferred (i.e. that this->obj
becomes null), e.g. MovePtr
.
The name GetPtr
makes it sound like it doesn't modify this->obj
and just returns a non-owning pointer to the managed object, i.e. that its behavior is the following:
Obj* GetPtr() const { return obj.get(); }
Upvotes: 7
Reputation: 41519
The unique
means actually 'unique ownership'. It makes no sense that you would create a copy of the ownership, since then it would not be unique anymore.
What you probably want is returning a reference to the contained object, or a non owning pointer:
class ObjHandler {
Object &get(){ return *obj; }
Object *GetPtr() { return obj.get(); }
private:
unique_ptr<Object> obj;
};
This post is a very good talk on the what/where/why of using smart pointers.
And the CppCoreGuidelines have a hint on this, too: a raw pointer is by definition indication of the fact that the object is not owned.
Upvotes: 10