Balan K
Balan K

Reputation: 356

How can a type with suppressed move construct/assign still be considered moveable?

struct copyable { // and movable
  copyable() = default;
  copyable(copyable const&) { /*...*/ };
  copyable& operator=(copyable const&) { /*...*/ return *this; }
};

Since the copy constructor and copy assignment operation functions are explicitly defined, it signifies that the move constructor and move assignment function cannot be implicitly defined by the compiler and hence the move operation is not allowed.

Can you please let me know whether my above understanding is correct?

Upvotes: 26

Views: 1681

Answers (1)

songyuanyao
songyuanyao

Reputation: 172884

it signifies that move constructor and move assignment function cannot be implicitly defined by the compiler

Yes that's right.

and hence move operation is not allowed.

No, move operations can still be performed via the copy constructor and copy assignment operator (though this may not be the case you expected), because an rvalue could always be bound to const&.

More precisely, class copyable is still MoveConstructible and MoveAssignable .

A class does not have to implement a move constructor to satisfy this type requirement: a copy constructor that takes a const T& argument can bind rvalue expressions.

If a MoveConstructible class implements a move constructor, it may also implement move semantics to take advantage of the fact that the value of rv after construction is unspecified.

and

The type does not have to implement move assignment operator in order to satisfy this type requirement: a copy assignment operator that takes its parameter by value or as a const Type&, will bind to rvalue argument.

If a MoveAssignable class implements a move assignment operator, it may also implement move semantics to take advantage of the fact that the value of rv after assignment is unspecified.

As @Curious pointed, you can declare the move constructor and move assignment operator delete explicitly to make copyable unmovable; then using with an rvalue expression the deleteed overload will be selected and compile would fail.

Upvotes: 31

Related Questions