繁体   English   中英

模板类上的 C++ 模板复制构造函数

[英]C++ template copy constructor on template class

我有一个模板类,它有一个模板复制构造函数。 问题是当我使用具有相同模板类型的此类的另一个实例实例化此类时,不会调用我的模板复制构造函数。 为什么不匹配?

这是代码片段:

#include <iostream>

template <typename T>
class MyTemplateClass
{
    public:
        MyTemplateClass()
        {
            std::cout << "default constructor" << std::endl;
        }

        /*
        MyTemplateClass(const MyTemplateClass<T>& other)
        {
            std::cout << "copy constructor" << std::endl;
        }
        */

        template <typename U>
        MyTemplateClass(const MyTemplateClass<U>& other)
        {
            std::cout << "template copy constructor" << std::endl;
        }
};

int main()
{
    MyTemplateClass<int> instance;
    MyTemplateClass<int> instance2(instance);
    return EXIT_SUCCESS;
}

输出是

default constructor

但是如果我显式地编写了默认的复制构造函数(通过取消注释),那么输出就变成了

default constructor
copy constructor

我真的不明白。 我用我的本地编译器(Clang 500.2.79)和这个(GCC 4.9.2)测试了它并得到了相同的结果。

复制构造函数的形式为X(X& )(X const&) ,如果您没有自己声明(或其他一些与此无关的条件),编译器将为您提供。 你没有,所以我们隐含地有以下一组候选人:

MyTemplateClass(const MyTemplateClass&);
template <typename U> MyTemplateClass(const MyTemplateClass<U>&);

两者都是可行的

MyTemplateClass<int> instance2(instance);

两者都采用相同的确切参数。 问题不在于您的复制构造函数模板不匹配 问题在于隐式复制构造函数不是函数模板,在重载解析方面,非模板比模板特化更受欢迎。 从 [over.match.best],省略不相关的要点:

鉴于这些定义,如果对于所有参数 i,ICS i (F1) 不是比 ICS i (F2) 更差的转换序列,那么一个可行函数 F1 被定义为比另一个可行函数 F2 更好的函数,然后
— [...]
— F1 不是函数模板特化,F2 是函数模板特化,或者,如果不是,
— [...]

这就是为什么它在构造函数模板上调用隐式(然后是显式)复制构造函数。

当您的代码中没有复制构造函数时,编译器将隐式生成它。 因此,当执行此行时:

MyTemplateClass<int> instance2(instance);

正在执行的拷贝构造函数,但显然不是你的。 我认为模板与它无关。

在此处阅读更多相关信息: 隐式定义的复制构造函数

我认为 REACHUS 是对的。 编译器正在生成一个默认的复制构造函数(就像使用非模板类一样)并且比模板更喜欢它,因为它更专业。

您应该将“普通”复制构造函数设为私有,或者更好的是,使用 C++11 'deleted' 关键字将该函数标记为不可用。

但是,这不会编译。 抱歉,我当时无法测试。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM