C ++:用户定义的显式类型转换函数错误

问题描述 投票:0回答:1

这是代码的外观:

using namespace std;
class dummy{
public:
    int x;
    explicit dummy(int x = 0) : x{ this->x = x } {}; //explicit has no effect here
};

class myClass {
public:
    operator int(); //<---problematic conversion
    explicit operator dummy();

};

myClass::operator int() {
    return 10;
}

myClass::operator dummy(){
    return dummy(9);
}

int main() {
    myClass mc1; 
    dummy val = (dummy)mc1;
    cout << "mc1 int cast: " << mc1 << endl; 
    cout << "val.x: :" << val.x << endl;
    std::cin.get();
    return 0;
}

我在这里使用ms vs编译器,并获取c2440(类型转换错误)。据我了解,我在语法上没有做任何错误的事情。这里的问题是,如果我从代码中删除隐式转换:operator int()及其相应的功能,它将可以正常工作。即:

using namespace std;
class dummy{
public:
    int x;
    explicit dummy(int x = 0) : x{ this->x = x } {}; //explicit has no effect here
};

class myClass {
public:
    //operator int();
    explicit operator dummy();

};
/*
myClass::operator int() {
    return 10;
}*/

myClass::operator dummy(){
    return dummy(9);
}

int main() {
    myClass mc1; 
    dummy val = (dummy)mc1;
    //cout << "mc1 int cast: " << mc1 << endl; 
    cout << "val.x: " << val.x << endl;
    std::cin.get();
    return 0;
}

这将产生以下输出(按预期):

val.x: 9

编辑:在第二个示例中缺少显式关键字。输出是相同的

c++ type-conversion user-defined-types
1个回答
0
投票

dummy类型的对象的创建方式之间存在歧义。

第一个是调用operator dummy创建类型为dummy的临时对象,然后由于显式强制转换而调用复制构造函数。

[第二个是由于myClass将类型int的对象转换为类型operator int,然后调用类myClass的转换构造函数以创建类型[ C0]。


0
投票

在ubuntu 18.04上用gcc-9编译您的原始代码,我明白了:

dummy

正在发生的情况是编译器无法确定您是要从myclass的int转换中创建新的'dummy'类,还是要从隐式生成的'dummy'的复制运算符中创建新的'dummy'。

这会导致一个循环,其中“ myClass”可以同时转换为test.cpp:27:24: error: call of overloaded ‘dummy(myClass&)’ is ambiguous 27 | dummy val = (dummy)mc1; | ^~~ test.cpp:7:14: note: candidate: ‘dummy::dummy(int)’ 7 | explicit dummy(int x = 0) : x{ this->x = x } {}; //explicit has no effect here | ^~~~~ test.cpp:4:7: note: candidate: ‘constexpr dummy::dummy(const dummy&)’ 4 | class dummy{ | ^~~~~ test.cpp:4:7: note: candidate: ‘constexpr dummy::dummy(dummy&&)’ int,这意味着在构造虚拟对象时,编译器会卡住尝试对其进行转换,因为它不知道您实际要做什么-新建一个'dummy',创建一个新的'myClass'并将其转换为'dummy'或创建一个新的'myClass'并将其转换为int

© www.soinside.com 2019 - 2024. All rights reserved.