枚举值的行为类似于全局变量吗?
我有两个枚举,如果一个枚举中有一个值与另一个枚举中的值同名:
enum A {joe, bob, doc};
enum B {sunday, monday, doc};
编译器(Visual Studio 的)抱怨 doc
的重新定义,这意味着它会处理它作为全局变量。是这样吗?这不是我期望的行为,它迫使我管理项目中所有枚举元素的名称。
任何见解都会有帮助。
I have two enums, and if there is one value in one enum with the same name as a value in the other enum:
enum A {joe, bob, doc};
enum B {sunday, monday, doc};
The compiler (Visual Studio's) complains about redefinition of doc
, which implies it treats it as a global variable. Is this so? It is not the behavior I would expect, and it forces me to manage names of all enum elements in my project.
Any insights would help.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(7)
它不被视为全局变量。变量。它被视为全局标识符。
更准确地说,它被视为声明
enum
的任何命名空间中的标识符。在您的情况下,这就是全局命名空间。要了解全局标识符和全局变量之间的区别,请尝试获取枚举的地址。 ;)
通常,当我定义枚举时,我会在前面添加标识符名称的缩写版本。像这样:
这有助于避免碰撞。
It's not treated as a global variable. It's treated as a global identifier.
More precisely, it's treated as an identifier in whatever namespace the
enum
is declared in. In your case, that's the global namespace.For an idea of what the difference is between a global identifier and a global variable, try taking the address of your enum. ;)
Usually when I define enums, I prepend the an abbreviated version of the name of the identifier. Like this:
This helps to avoid collisions.
Wyatt Anderson 已经建议
修复“枚举值与枚举本身在同一范围内”问题,允许您编写
但是当您想要本地的
enum
时,此解决方案不可用类,至少在类外部引入人工命名空间的情况下是这样。一个简单的解决方案是将每个
enum
包装在一个结构中,如下所示:这允许与命名空间解决方案相同的使用符号,
但它还允许
在类中定义,
通过继承将枚举名称直接带入类,
限定符的本地类重命名,通过
typedef
。另外,在我看来,上面示例的命名约定
A::Enum
。好的,命名约定也可以与基于名称空间的解决方案一起使用......
干杯&呵呵,,
Wyatt Anderson has already suggested
as a fix for the "enum values are in the same scope as the enum itself" problem, allowing you to write
But this solution is not available when you want an
enum
local to a class, at least not without introducing an artificial namespace outside the class.A simple solution is to instead wrap each
enum
in a struct, like so:This allows the same usage notation as with the namespace solution,
but it additionally allows
definition within a class,
bringing the enumeration names directly into a class via inheritance, and
local-in-class renaming of the qualifier, via
typedef
.Plus, the naming convention exemplified above allows
A::Enum
.OK, the naming convention can also be used with the namespace based solution…
Cheers & hth.,
C++03 中的枚举数与枚举具有相同的作用域。
这有时很方便,有时则不太方便。
在 C++0x 中,我们将拥有
枚举类
,它更像 C# 的枚举
。同时,假设(因为这是语言规则)yyy
和zzz
与xxx
具有完全相同的范围Enumerators in C++03 have the same scope as the enumeration .
This is sometimes convenient, sometimes not really.
In C++0x we will have
enum class
es which are more like C#'senums
. In the meantime, just assume (cause that's the language rule) thatyyy
andzzz
have exactly the same scope asxxx
如果您希望它们是全局的,请通过将
enum
放入命名空间来解决您的问题并避免命名空间污染:If you want them to be global, fix your problem and avoid namespace pollution by throwing your
enum
s in a namespace:枚举的值存在于声明枚举的任何范围内。
例如,以下工作:
或
The values of an enumeration exist in whatever scope the
enum
was declared in.The following works, for example:
or
枚举的值具有枚举本身的范围,即它的声明范围。例如:
x 将为 32。
The enum's values have the scope of the enum itself, that is, it's declaration scope. For example:
x will be 32.
假设我们要声明图形窗口的纵横比。然后按照已经建议的方式定义枚举值:
最后的
typedef
允许我们使用AspectRatio::ASPECT_RATIO_16_9
作为函数签名的简写:这对我来说完全有效正如我在 C# 中所期望的那样。
编辑:
假设您使用至少 C++11,那么您最好声明一个
枚举类
:它是一种类型安全的替代方案,不会污染封闭的环境范围。还应该注意的是,为了防止与全局定义的宏发生名称冲突,
enum class
值通常不应使用ALL_CAPS
命名约定。Let's say we want to declare aspect ratio for a graphical window. Then defining the enum values as already suggested:
The
typedef
in the end allows us to useAspectRatio::ASPECT_RATIO_16_9
as a shorthand for, e.g. function signatures:This works for me exactly as I would expect it to in C#.
Edit:
Assuming that you are using at least C++11, then you are better off declaring an
enum class
:It's a type-safe alternative that does not pollute the enclosing scope. It should also be noted that, in order to prevent name clashing with globally defined macros,
enum class
values should usually not use theALL_CAPS
naming convention.