Search code examples
c++templatescopy-constructormisra

Why must I have a copy constructor if there is a template constructor with a single parameter that is generic?


MISRA rule 14-5-2 says:

A copy constructor shall be declared when there is a template constructor with a single parameter that is a generic parameter.

I can't find anything that explains to me in simple enough terms why there must be a copy constructor in such a case.

I've looked at Copy constructor of template class and C++ Template constructor, why is copy constructor being called?, but neither really helped me. I see mention that a copy constructor wouldn't exist, but doesn't the default one still get created? I saw references to copy elision, but I don't understand why the copy constructor is necessary for it.

As far as I can tell, this could fall under "good programming practice to watch out for"... or it could be "you've just entered into undefined behavior land". What should I look for to determine if the code that is violating this MISRA rule is causing a risk in its current code base?


Solution

  • Unless you write a move constructor or move assignment operator, a copy constructor is always defined (possibly as deleted - or undefined prior to C++11). If you don't declare it yourself, it is auto-generated.

    Now, I don't know enough about MISRA to be sure of the reasoning behind the rule you mention, so I'm going to guess what it is. If you have a template constructor with a single and generic parameter, then you might be doing more than a simple copy, and you may incorrectly think that all copy constructions will be done through this template constructor. But if you copy-construct an object of that class (the one with the template constructor) with another object of that same class or one derived from it, then the auto-generated copy constructor will be called, and none of the extra work that the template version is supposed to do will be done.

    In short, by providing a copy constructor even when also providing a template constructor with a single and generic parameter, you make sure that copy constructions always work as intended. Moreover, you explicitly show the potential users of the class that it has a proper copy constructor in addition to the template constructor.