过载分辨率和用户定义的转换

Ang*_*tis 8 c++ overload-resolution

考虑一下简单的代码:

struct A;
struct B {
  B(){}
  B(A const&){ }
};

struct A {
  operator int() const {return 0;};
};
void func(B){}
void func(char){}

int main()
{
func(A()); //ambiguous call oO
}
Run Code Online (Sandbox Code Playgroud)

首先,我不确定我是否理解正确的一切,所以当你发现我错了时请纠正我.

我的理解是,该void func(B)已选定,由于参数funcA它是类的类型,因此需要转换的类型是"用户定义的转换序列"

现在来自IBM C++ ref:

用户定义的转换序列包括以下内容:

  • 标准转换序列
  • 用户定义的转换
  • 第二个标准转换序列

现在有两个用户定义的转换存在 B::B(const A&)A::operator int (const A&);

所以顺序是

- > A()- > B::B(const A&)- >Standard conversion (identity conversion)

- > A()- > A::operator int (const A&)- >Standard conversion (integral conversion)

因为积分转换比我认为void func(B)会调用的身份转换更糟糕,但仍然调用是模糊的.

所以,请帮助我,我错了,为什么电话不明确.非常感谢 :)

M.M*_*M.M 6

这里有两个转换序列,A -> B并且A -> int都是用户定义的,因为它们通过您定义的函数进行操作.

用户定义的转换序列排序规则见13.3.3.2(N3797):

用户定义的转换序列U1是比另一个用户定义的转换序列更好的转换序列,U2如果它们包含相同的用户定义的转换函数或构造函数,或者它们在聚合初始化中初始化相同的类,并且在任何一种情况下,第二个标准转换序列U1是优于第二标准转换序列U2

这两个转换序列不包含相同的用户定义转换函数,并且它们不会在聚合初始化中初始化相同的类(因为一个初始化int).

因此,一个序列排在另一个之上并不是真的,因此这个代码是模糊的.