在隐式类型转换期间,最多可以隐式应用多少用户定义的转换运算符?

Dán*_*dor 2 c++ language-lawyer implicit-conversion c++11 g++4.8

根据N3337工作草案(与已发布的ISOC++ 11标准最相似的草案),答案最多只有一个.

N3337:

最多一个用户定义的转换(构造函数或转换函数)隐式应用于单个值.

[ Example:

struct X {
    operator int();
};

struct Y {
    operator X();
};

Y a;
int b = a; // error
           // a.operator X().operator int() not tried

int c = X(a); // OK: a.operator X().operator int()

—end example ]
Run Code Online (Sandbox Code Playgroud)

但根据使用gcc(Ubuntu 4.8.4-2ubuntu1~14.04)4.8.4编译main.cpp并在Ubuntu 14.04.3 LTS中使用引用语句运行a.out结果,答案最多不是一个.

main.cpp:

#include <iostream>

struct As
{
    operator int(){ std::cout<<"operator As::int()"<<std::endl; return 1; }
};

struct Bs
{
    operator int(){ std::cout<<"operator Bs::int()"<<std::endl; return As(); }
};

int main()
{
     int i=Bs();

     return 0;
}
Run Code Online (Sandbox Code Playgroud)

从终端编译和运行:

$ g++ -std=c++11 main.cpp
$ ./a.out
Run Code Online (Sandbox Code Playgroud)

结果(输出):

operator Bs::int()
operator As::int()
Run Code Online (Sandbox Code Playgroud)

我是否误解了某些内容或N3337是否错误或者gcc是否包含错误?

Sam*_*hik 5

这里没有双重转换执行.

您可以在两个不同的位置进行两次单独转换.

一次转换是在B::operator int().

第二次转换是在你的main().

让我们试着从逻辑上思考:

完全从翻译单元中删除main().你看到任何双重转换吗?

没有.

现在,让我们创建一个包含以下位的头文件,调用它structures.H:

struct As
{
    operator int();
};

struct Bs
{
    operator int();
};
Run Code Online (Sandbox Code Playgroud)

现在,创建一个structures.C文件,其中包含每个运算符的内容:

#include <structures.H>

B::operator int(){ std::cout<<"operator As::int()"<<std::endl; return 1; }
A::operator int(){ std::cout<<"operator Bs::int()"<<std::endl; return As(); }
Run Code Online (Sandbox Code Playgroud)

好的,你还能在这里看到任何双重转换吗?没有.

现在,创建你的main.C:

#include <structures.H>

int main()
{
     int i=Bs();

     return 0;
}
Run Code Online (Sandbox Code Playgroud)

你看到在这里发生了双重转换吗?不,即使我们现在拥有两个翻译单元,您开始使用相同的确切代码.