如果我这样做:
MyClass a=b;
这使用复制构造函数初始化a
,并且不涉及=
运算符重载,对吗?
如果=
已初始化,则会使用a
运算符,然后我将其分配给其他人。
我看到this:
S(std::initializer_list<T> l) : v(l) {
用过:
S<int> s = {1, 2, 3, 4, 5}; // direct list-initialization
这很有趣。它是初始化,它使用=
运算符,但它调用的是不是复制构造函数的构造函数。为什么不采用这样的语法:
S<int> s {1, 2, 3, 4, 5};
具有std::vector
的{{1}} constructor的工作方式。当该运算符没有调用复制构造时,使用std::initializer_list
运算符初始化对象似乎很困惑,不是吗?
答案 0 :(得分:11)
这使用复制构造函数来初始化a,并且不涉及=运算符重载,对吗?
完全。
为什么不采用这样的语法:[...]
您可以使用这两种形式,它们大多是等效的,除了使用=
的表单称为 copy-list-initialization 这一事实,它需要非{ {1}}构造函数(感谢Nicol Bolas的更正)。
另一方面,没有explicit
的表单被称为 direct-list-initialization ,它通过直接从初始化程序构建对象(非常直观地)工作(传递初始化程序作为要初始化的对象的构造函数的参数。构造函数是否为=
与此无关。
简而言之,除了 copy-list-initialization 在构造函数为explicit
时不会起作用的事实外,这两种形式是等效的。如果不是这种情况,选择哪种形式主要是风格问题。
答案 1 :(得分:3)
MyClass a=b;
类型为b
时, MyClass
才会使用复制构造函数。
如果b
是OtherClass
,则需要另一个构造函数,它不是复制构造函数,只需要另一个以OtherClass
作为参数的自定义构造函数(或更可能const OtherClass&
,但这与问题无关 - 只是防止挑剔者:)。
与initializer_list
的示例相同:它是类型S
的普通构造函数,它将初始化列表作为参数。从这个意义上说,它与一些假设的构造函数S(int n)
没有区别。
想象一下,如果你有:
S(int n) : v(n) {} // ctor taking an int
你可以创建一个这样的实例:
S s = 4;
初始化列表也是如此。