隐式构造函数转换似乎只适用于单个转换。
class A {
public:
A(std::string s) {}
};
class B {
public:
B(A a) { }
};
使用上面的代码,运行
B b{std::string("Hey")};
工作正常。
另一方面,
B b{"Hey"};
才不是。
构造函数转换是否真的只适用于一次转换,为什么会这样?为了避免在提供不同的构造函数时可能产生歧义?
构造函数转换真的只适用于单次转换吗?
一个用户定义的转换,是的。它还可能涉及该转换之前或之后的标准转换。
为什么会这样?
简单的答案是因为这就是指定语言的方式。
更有用的是:如果允许两次转换,那么编译器将不得不考虑它知道的每种类型,以确定是否存在合适的中间类型。这不仅需要大量的工作(组合爆炸,如果您允许任意数量的转换),而且您可能会得到模棱两可,以及行为的细微变化,具体取决于当时恰好定义了哪些类型编码。
B b{"Hey"};
需要转换为std::string
,然后转换为A
,这是两次转换。
构造函数转换是否真的只适用于一次转换,为什么会这样?
是的。这就是标准所要求的。
[class.conv]/4:
最多一个用户定义的转换(构造函数或转换函数)被隐式应用于单个值。