16

在 c 和 c++enum中都可以用标签定义

enum e_smth {
    smth_one,
    smth_two,
    smth_err
};

或无标签

enum {
    smth_one,
    smth_two,
    smth_err
};

switch如果它是用标记定义的,那么在 c 和 c++ 中的语句中都是有意义的:

e_smth some_var;
....//do some stuff with some_var
switch (some_var)
{
case smth_one:
break;
case smth_two:
break;
}

-Wswitch如果这将使用 gcc 或 g++ 编译, 将产生 警告。

在 c++ 中的函数声明和变量初始化中是有意义的:

e_smth var;
var=99;

如果使用 g++ 编译会产生-fpermissive错误。

带标签或不带标签的两种类型都可以用作一个#define不带参数的文件宏。


更新

可以作为一个文件#define宏使用,不带参数

意思是:而不是#define MAX 1000在文件中写入并将 MAX 添加到enum { MAX=1000 }仅在文件范围内的全局使用中


那么匿名枚举呢,我只发现了一个用例:定义就像typedef enum { a,b,c } some_t;使它像带有标签的枚举一样工作

问题:

如果我还没有描述所有合理的用例,应该使用什么匿名枚举?

4

4 回答 4

19

在 C 中(但不是在 C++ 中),enum可以 [ab] 用于定义int常量。

例如,给定这个声明:

const int MAX = 1024;

MAX不是常量表达式,它是只读对象的名称。这意味着您不能在 case 标签中使用它,作为在文件范围或 with 声明的数组的大小static,或在任何其他需要常量表达式的上下文中。

但是如果你写:

enum { MAX = 1024 };

thenMAX type 的常量表达式int,可在任何可以使用该常量的上下文中使用1024

当然你也可以写:

#define MAX 1024

但是使用预处理器也有一些缺点:例如,标识符的范围没有像普通声明那样。

缺点是这样的常量只能是 type int

C++有不同的规则;枚举常量属于枚举类型,not int,但您可以将声明的常量对象用作常量表达式(只要初始化程序是常量表达式)。

为了解决最初的问题,当您使用enum声明来创建这样的常量时,使用标签或 typedef 是没有意义的,因为您永远不会使用类型本身。

背景:这个:

enum foo { zero, one, two };
enum foo obj = two;

创建一个类型enum foo和常量zero, one, 和two. 在 C 中,常量始终是 类型int,这无疑是奇怪的,并且 的初始化涉及从到obj的隐式转换。intenum foo

在C++中,类型enum foo也可以称为just foo,常量是类型enum foo(兼容某些整数类型,不一定int)。

于 2012-04-14T20:54:00.453 回答
5

另一个用例是作为structor的一个元素union,通常当它本身没有意义时(因为它只是为了满足通信协议的 ABI 等而存在,并且对于编程使用有更合适的表示)。

于 2012-04-14T20:42:41.080 回答
0

@eith汤普森

您的答案是“const int MAX = 1024; MAX 不是常量表达式”。但是,链接http://en.cppreference.com/w/cpp/language/constant_expression中的示例 表明它是一个常量表达式,可以在数组声明中使用。常量表达式 C++ C++ 语言表达式 定义一个可以在编译时求值的表达式。

此类表达式可用作非类型模板参数、数组大小以及其他需要常量表达式的上下文,例如

int n = 1;
std::array<int, n> a1; // error, n is not a constant expression
const int cn = 2;
std::array<int, cn> a2; // OK, cn is a constant expression
于 2016-07-28T17:56:37.120 回答
0

通常,您只需要在多次使用枚举时为其命名。换句话说,如果您使用同一个枚举定义多个变量,那么您需要命名该枚举。但是,如果您只使用一次枚举并且只有一个变量具有该枚举,那么匿名枚举是有意义的。例如:

enum color { red, blue, gray, green };
enum color car_color;
enum color house_color;

这里有多个变量,所以命名枚举。

typedef struct {
    int year;
    enum { Jan, Feb, Mar, Apr, May, Jun, July, Aug, Sep, Oct, Nov, Dec } month;
    unsigned int day;
} date;

这里作者计划只使用一次枚举,所以没有必要命名。

于 2019-04-11T20:10:32.980 回答