Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why should I delete move constructor and move assignment operator in a singleton?

Tags:

I have the following Singleton policy-class implementation:

template <typename T> class Singleton {     Singleton(){}; // so we cannot accidentally delete it via pointers     Singleton(const Singleton&) = delete; // no copies     Singleton& operator=(const Singleton&) = delete; // no self-assignments     Singleton(Singleton&&) = delete; // WHY?     Singleton& operator=(Singleton&&) = delete; // WHY? public:     static T& getInstance() // singleton     {         static T instance; // Guaranteed to be destroyed.                        // Instantiated on first use.                        // Thread safe in C++11         return instance;     } }; 

which I then use via the curiously recurring template pattern (CRTP)

class Foo: public Singleton<Foo> // now Foo is a Singleton {     friend class Singleton<Foo>;     ~Foo(){}     Foo(){}; public: // rest of the code }; 

I cannot figure out why I should delete the move constructor and assignment operator. Can you give me a single example where I end up breaking the singleton if I don't delete (don't define at all) the move ctor and assignment operator?

like image 742
vsoftco Avatar asked May 20 '14 22:05

vsoftco


People also ask

Why do you need a move constructor?

A move constructor enables the resources owned by an rvalue object to be moved into an lvalue without copying.

Which is true about move operations move constructor move assignment operator?

The move constructor and move assignment operator are simple. Instead of deep copying the source object (a) into the implicit object, we simply move (steal) the source object's resources. This involves shallow copying the source pointer into the implicit object, then setting the source pointer to null.

Why is the constructor and copy constructor private in the Singleton class?

The constructor, copy constructor and assignment operator are all private to ensure that the programmer using the singleton class can only create a single instance of the class using only the Instance() function.

What is the point of a move constructor C++?

A move constructor allows the resources owned by an rvalue object to be moved into an lvalue without creating its copy. An rvalue is an expression that does not have any memory address, and an lvalue is an expression with a memory address.


1 Answers

If you declare a copy constructor (even if you define it as deleted in the declaration), no move constructor will be declared implicitly. Cf. C++11 12.8/9:

If the definition of a class X does not explicitly declare a move constructor, one will be implicitly declared as defaulted if and only if

— X does not have a user-declared copy constructor,

— ...

Since you do have a user-declared copy constructor, there won't be a move constructor at all if you don't declare one. So you can just get rid of the move constructor declaration-definition entirely. Same for the move-assignment operator.

like image 143
Kerrek SB Avatar answered Nov 02 '22 06:11

Kerrek SB