我的枚举不是一个类或命名空间。

62

你好,我有名为MyCode.h和MyCode.cpp的文件。

在MyCode.h中,我已经声明了:

enum MyEnum {Something = 0, SomethingElse = 1};

class MyClass {

MyEnum enumInstance;
void Foo();

}; 

然后在MyCode.cpp文件中:

#include "MyCode.h"

void MyClass::Foo() {
    enumInstance = MyEnum::SomethingElse;
}

但是在使用g++编译时,我收到了错误消息:“MyEnum”不是类或命名空间......

(在MS VS2010中可以正常工作,但在Linux g++中无法工作)

有什么想法吗? 谢谢 托马斯


1
注意:在您的.cpp文件中,如果您想为MyClass::foo提供实现,则签名应为void MyClass::Foo() { ... }。您缺少了MyClass::这一部分。 - phooji
MyCode.h != MyClass.h ... 但是我怀疑这并没有什么帮助 :P - deceleratedcaviar
4个回答

67

MyEnum::SomethingElse的语法是微软的扩展功能。我很喜欢它,但它不是标准C++。 enum值被添加到周围的命名空间中:

 // header
 enum MyEnum {Something = 0, SomethingElse = 1};

 class MyClass {

 MyEnum enumInstance;
 void Foo();

 }

 // implementation
 #include "MyClass.h"

 void Foo() {
     enumInstance = SomethingElse;
 }

7
幸运的是,C++0x将添加这种功能,我认为很长一段时间以来都缺乏并迫切需要。 - Sion Sheevok
1
谢谢。这让我疯了。我无法弄清楚为什么我的枚举在一个XCode项目中可以解决而在另一个项目中却不行。O.o 虽然我仍然不知道为什么会发生这种情况,但我知道如何修复。如果有人能猜到原因,我将非常乐意知道。 - javatarz

51

直到C++0x才引入了作用域枚举。目前,您的代码应该是:

enumInstance = SomethingElse;

你可以通过将枚举定义放置在其自身的命名空间或结构体中,来创建一个人工作用域的枚举。


31

确实,C++0x允许使用这个特性。我可以通过使用命令行标志-std=c++0x在gcc中成功启用它。

这是在gcc版本4.4.5中实现的。


1
谢谢,帮我节省了时间。 - X-HuMan

2

如其他答案所解释的那样:在普通的C++98枚举中,语法MyEnum::SomethingElse是无效的,除非您的编译器通过非标准扩展支持它们。

我个人不喜欢声明enum MyEnum {A, B};,因为在使用枚举值时没有类型名称。这可能会导致当前命名空间中名称的冲突。

因此,用户应在每个枚举值处引用类型名称。例如,避免声明两次A:

enum MyEnum {MyEnum_A, MyEnum_B};
void A(void) {
    MyEnum enumInstance = MyEnum_A;
}

我更喜欢使用特定的命名空间或结构。这样可以使用最新的C++风格引用枚举值:

namespace MyEnum {
    enum Value {A,B};
}
void A(void) {
    MyEnum::Value enumInstance = MyEnum::A
}

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接