c – 用于虚函数返回的枚举变量
作者:互联网
为什么C不能识别枚举MyEnum:int作为int的共变体?
#include <iostream>
enum FooType : int
{
Crazy = 0,
Cool
};
enum BarType : int
{
Hello = Cool + 1,
World
};
class Foo
{
public:
Foo(void)
{
}
~Foo(void)
{
}
virtual int getType(void)
{
return Crazy;
}
};
class Bar : public Foo
{
public:
Bar(void)
{
}
~Bar(void)
{
}
virtual BarType getType(void)
{
return Hello;
}
};
int main(int argc, char* argv[])
{
Bar f = Bar();
std::cout << f.getType() << std::endl;
return 0;
}
编译错误:
prog.cpp:43:18: error: conflicting return type specified for 'virtual BarType Bar::getType()'
prog.cpp:26:14: error: overriding 'virtual int Foo::getType()'
解决方法:
非范围的枚举类型(即通常的枚举,而不是枚举类和枚举结构)提供对整数的隐式提升,即您可以这样做:
enum FooType : int { Crazy, Cool };
int val = Crazy; // promotion to integer
但是,这不起作用:
FooType val = 0; // illegal
这遵循§7.2/ 5:每个枚举定义一个与所有其他类型不同的类型,结合§7.2/ 9:枚举器的值或未作用域的枚举类型的对象通过整数提升转换为整数.
我相信这条规则的原因很明显:可以有(通常是)整数值,没有定义相应的枚举数.在上面的示例中,理论上可以转换0和1,但无法转换转换2或任何更大的数字.
但是,如果枚举与其基础类型(在您的示例中为int)协变,则在您定义它的意义上,以下是可能的:
class Foo
{
public:
virtual ~Foo(void) {}
virtual int getType(void)
{
return Crazy;
}
};
class Bar : public Foo
{
public:
virtual ~Bar(void) {}
virtual BarType getType(void)
{
return Foo::getType();
}
};
在派生类中,Bar :: getType()现在已被定义为返回BarType,但它通过调用继承的函数Foo :: getType()来完成此操作,这完全是合法的.
如果这是可能的,那么Bar :: getType()必须将从Foo :: getType()得到的int隐式转换为int.如上所述,这不可能.
但是,您仍然可以通过以与Foo:getType相同的方式声明Bar :: getType来实现您的代码似乎意图,并返回一个BarType(隐式提升为int):
class Bar : public Foo
{
public:
virtual ~Bar(void) {}
virtual int getType(void)
{
return Hello;
}
};
请注意,这仅在底层类型为int时才有效(因为它是在枚举声明中将其固定为int),并且枚举不是作用域的(即不使用枚举类或枚举结构).
标签:c,c11,enums,covariance 来源: https://codeday.me/bug/20190723/1511324.html