假设有一个基类,它在头文件中定义了如下所示的枚举:
class Base{
public:
Base();
enum MyEnum1{
A_VALUE=1,
B_VALUE=2
};
};
派生类在不同的枚举中定义相同的变量但具有不同的值:
class Derived : public Base{
public:
Derived();
enum MyEnum2{
A_VALUE=3,
B_VALUE=4
};
};
显然我犯了一个错误,因为我没有注意到A_VALUE和B_VALUE已经在基类中定义了。 然后我在派生类实现中使用了这些值。 为什么我没有被编译器(Visual Studio 2013)警告该值存在冲突?我可以认为我使用的是MyEnum2而不是MyEnum1的值,反之亦然。
答案 0 :(得分:0)
给出以下代码:
#include <iostream>
class Base
{
public:
enum MyEnum1
{
A_VALUE = 1,
};
const int B_VALUE = 42;
int C_VALUE = -2;
};
class Derived : public Base
{
public:
enum MyEnum2
{
A_VALUE = 3,
};
const int B_VALUE = 180;
int C_VALUE = 99;
void test()
{
std::cout << A_VALUE << ' ';
std::cout << static_cast<const Base*>(this)->A_VALUE << ' ';
std::cout << B_VALUE << ' ';
std::cout << static_cast<const Base*>(this)->B_VALUE << ' ';
std::cout << C_VALUE << ' ';
std::cout << static_cast<const Base*>(this)->C_VALUE << std::endl;
}
};
int main()
{
Derived instance;
instance.test();
}
3 1 180 42 99 -2
将被打印。
这是因为标识符Derived::A_VALUE
会影响Base::A_VALUE
的标识符,因此必须对基类型进行显式强制转换才能访问它。这同样适用于在类范围内定义的其他名称,无论constness如何。
为什么这不会产生警告取决于您正在使用的实现,但可能会有一个可变的阴影警告,可以涵盖这种情况。但是,该标准没有任何警告概念,因此没有客观答案为什么您的特定编译器不在此处(除非您向实施者发送消息并询问,即是)。
正如其他人所说,强类型枚举(C ++ 11)没有这样的问题,因为它们必须通过作用域解析运算符::
来访问,就像在命名空间中定义常量一样。