C++ Logo

std-proposals

Advanced search

user copy constructor

From: Bengt Gustafsson <bengt.gustafsson_at_[hidden]>
Date: Thu, 12 Dec 2019 23:06:19 +0100
I like the concept, but I think the syntax should be more like what we
use to define that the default constructor should be defaulted. It also
needs to work for move constructors and preferably for assignment
operators. One possible syntax would be:

class Foo {
   std::vector<int> first;
   std::list<int> second;
   ...
   void *no_copy;

   Foo(const Foo &) : default, no_copy(nullptr) {}
   Foo(Foo&&) : default, no_copy(nullptr) {}
};

The default word is to be interpreted as doing a meberwise copy construction for those members not explicitly mentioned, which is similar to how initialized member declarations or with this lacking default construction is used for unmentioned members today. So the word default indicates that instead of defaulting to initiation (or default construction) for unmentioned members copying/moving should be done. Of course it should be legalt to not mention any members for a copy constructor which is to copy all members but then in addition do something in the function body. This may be just as valuable as the original use case:

    Foo(const Foo&) : default { log("Copy constructed yet another Foo"); }


Extending this to the assignment operator would be nice but is not so easy as there is no specific syntax to denote the actual copying of each member. The only solution I could think of right now is to start allowing the same syntax as for constructors, but with the meaning changed to for each mentioned member do an assignment rather than a construction, of course. This would allow us to write simplified assignment operators in the same way:

    Foo& operator=(const Foo& src) : default, first=vector{1, 2}, no_copy= {}

Here I diverged from the initializer syntax and use = to emphasize that there is assignment going on. Furthermore I dream up the syntax member= to indicate that the member in question should not be touched. This seems rather ugly so maybe for this case the original syntax of ! is better:

    Foo& operator=(const Foo& src) : default, second=second+src.second, !no_copy {}

For orthogonality reasons you would not have to mention default but could use this member-assignment-list syntax as an alternative to writing assignment statements inside the body. One possible benefit would be that compilers could issue warnings if any members are missed in the list (and no default is mentioned).

Indeed this is a separate feature that warrants its own proposal, which then would reasonably incorporate the original proposal's default based syntax extension.
  
Bengt

Received on 2019-12-12 16:08:38