C++ 显式和非显式构造函数

C++ 显式和非显式构造函数,c++,constructor,copy-constructor,explicit,copy-initialization,C++,Constructor,Copy Constructor,Explicit,Copy Initialization,我观察到不同的结果。 案例1:注释第1行和第2行时,o/p为: 构造函数调用 构造函数调用 案例2:当第1行和第2行未注释时:则编译错误 有人能解释一下结果和原因吗。还有人可以判断operator=是否真的调用了复制构造函数。测试u=0是转换构造函数的情况。详情请参阅。 在删除注释后,我尝试编译注释行,它为我编译。我使用的是gcc版本4.3.4。您正在使用哪个版本的编译器?您的问题在于下面的显式构造函数,以及对对象初始化的一点误解 根据这一说法: class Test { pub

我观察到不同的结果。 案例1:注释第1行和第2行时,o/p为: 构造函数调用 构造函数调用

案例2:当第1行和第2行未注释时:则编译错误


有人能解释一下结果和原因吗。还有人可以判断operator=是否真的调用了复制构造函数。

测试u=0是转换构造函数的情况。详情请参阅。 在删除注释后,我尝试编译注释行,它为我编译。我使用的是gcc版本4.3.4。您正在使用哪个版本的编译器?

您的问题在于下面的显式构造函数,以及对对象初始化的一点误解

根据这一说法:

class Test
    {
    public:
        Test(int i) { cout<<"constructor called\n";}
        Test(const Test& t) { cout<<" copy constructor called\n";}
    };
 class Test1
        {
        public:
            Test1(int i) { cout<<"constructor called\n";}
            explicit Test1(const Test1& t) { cout<<" copy constructor called\n";}
        };

    int main()
    {
        Test t(0);  
        Test u = 0;
        //Test1 t1(0);   Line 1
        //Test1 u1 = 0;  Line 2

    }
将始终执行此类对象的复制初始化,这意味着:

Type variableName = value;
将使用参数Test1int有效地调用重载构造函数Test1::Test1const Test1&,从而生成u1::Test1Test10

此外,由于您将复制构造函数声明为显式,因此复制样式初始化将失败,但是:

Test1 u1 = 0;

将编译,因为该表达式调用方向初始化,即使Test1int将被标记为显式,直接初始化也是显式的,因此每个片段都匹配。

我观察到不同的输出。-和什么不同?跑步之间有什么不同?有人能解释一下结果吗?你为什么不给我们看看你看到的结果,这样我们就可以确定我们在解释你感兴趣的东西?if operator=实际上最终调用了复制构造函数-如果你放了一个cout,你观察到了什么输出?在任何情况下,运算符=都不同于复制构造函数,此处不使用。可能重复:显式复制构造函数是一个荒谬的组合,它没有任何用处。请注意,术语“复制初始化”并不总是意味着复制或移动!如果value已经有type类型,或者类型为的派生类,则没有临时对象,并且为variableName调用构造函数,该构造函数直接获取value.Test1 u1tmp;没有完全抓住本质,因为即使没有发生拷贝省略,如果类有移动,ui也将从tmp构建constructor@MattMcNabb:谢谢!我将进行编辑,以表示这只适用于Test1U1TMP中的tmp是左值的情况。但我看不出你的第一个音符有什么意义。你能解释清楚一点吗?如果我理解正确的话,你说在测试u1tmp中不一定是临时的,尽管我不明白你为什么这么说,因为这与我的ANWR完全无关。哈?在测试1中,tmp0;,tmp总是左值的。但这与test1u1=0;无关;。tmp是你编出来的。我认为您试图以一种非常复杂的方式说,Test u1=0与Test u1=Test0相同,其中有一个临时对象Test0。我的第一个评论是,在某些情况下没有临时对象。你的新子句给定了这个值。。。没有意义,而且无论如何都是错误的,因为类型variableName=value;始终执行复制初始化,无论值是什么。gcc 4.3是C++11之前的版本。使用至少4.5,最好是最新版本
Test1 t1(0);