考虑以下程序:
struct A {
A(int){}
A(A const &){}
};
int main() {
A y(5);
}
变量y
用表达式5
直接初始化。重载分辨率选择了构造函数A::A(int)
,这是我期望和想要的,但是为什么会发生呢? / p>
可能有两个原因:
过载A::A(int)
比A::A(A const &)
更合适,或者第二个过载根本不是可行的过载。
问题:在上面的程序中,构造函数A::A(A const &)
是y
初始化的可行重载吗?
答案 0 :(得分:6)
是的,构造函数重载的规则与普通函数相同。允许编译器为每个参数(如Ben Voigt所指出的那样)对每个参数进行转换,以便使参数与参数匹配。在这种情况下,它可以执行int->A
至A(5)
这种情况与:
void foo(const std::string&);
void bar(const std::string&);//1
void bar(const char*);//2
//...
foo("Hello");//Is allowed
bar("Hello");//Calls 2 as it matches exactly without a need for conversion.
因此,答案是肯定的,它是可行的重载,但未选择它,因为根据overloading rules,A(int)
构造函数是更好的匹配。
答案 1 :(得分:2)
一个不明确的构造函数([dcl.fct.spec])指定一个 从其参数类型(如果有)转换为 它的班级。这样的构造函数称为转换构造函数。
[示例:
struct X { X(int); X(const char*, int =0); X(int, int); }; void f(X arg) { X a = 1; // a = X(1) X b = "Jessie"; // b = X("Jessie",0) a = 2; // a = X(2) f(3); // f(X(3)) f({1, 2}); // f(X(1,2)) }
-示例]
和
假设“ cv1 T”是要初始化的对象的类型,而T是类类型,则候选函数的选择如下:
(1.1)T的转换构造函数是候选函数。