假设我没有在 Beatle
类中指定复制构造函数和 operator=
,以下两个声明有什么区别?
披头士约翰(保罗);
和
Beatle john = paul;
编辑:
在对象赋值中,运算符 =
隐式调用复制构造函数,除非另有说明?
最佳答案
它们是不同的语法结构。第一种是直接初始化,第二种是复制初始化。它们的行为几乎相同,只是第二个需要一个非显式
构造函数。*
两者都与赋值运算符无关,因为这两行都是初始化。
也就是说:const int i = 4;
很好,但是 const int i; i = 4;
不是。
*) 更准确地说:如果相关构造函数声明为显式
,则第二个版本不起作用。因此,更一般地说,直接初始化为您提供了一次“免费”转换:
struct Foo { Foo(std::string) {} };
Foo x("abc"); // OK: char(&)[4] -> const char * -> std::string -> Foo
Foo y = "abd"; // Error: no one-step implicit conversion of UDTs
解决您的编辑问题:要了解赋值运算符,只需将其分解成多个部分即可。假设 Foo
有明显的 operator=(const Foo & rhs)
。我们可以说 x = y;
,它只是直接调用运算符,其中 rhs
为 y
。现在考虑一下:
x = "abc"; // error, no one-step implicit conversion
x = std::string("abc"); // fine, uses Foo(std::string), then copy
x = Foo("abc"); // fine, implicit char(&)[4] -> const char* -> std::string, then as above
关于c++ - 在堆栈上声明对象的两种方式之间的区别,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/8194861/