是否需要C enum中的最后一个逗号?
C enum声明中是否需要最后一个逗号?
ie是VAL3
要求后的逗号?
enum { Val1, Val2, Val3, } someEnum;
将其留入/取出是否有任何副作用
谢谢
这不是必需的。 C99的6.7.2.2
节将语法列为:
enum-specifier: enum identifieropt { enumerator-list } enum identifieropt { enumerator-list , } enum identifier enumerator-list: enumerator enumerator-list , enumerator enumerator: enumeration-constant enumeration-constant = constant-expression
注意enum-specifier
的前两种forms,一种是逗号,另一种是逗号。
我见过使用它的一个好处是:
enum { Val1, Val2, Val3, } someEnum;
其中,如果要添加(例如) Val4
和Val5
,只需复制并粘贴Val3
行,而不必担心调整逗号。
并且,正如评论中所指出的,它也可以简化自动代码生成器,以便它们不必对最终值进行特殊处理。 他们可以输出每个值后跟逗号。
这可以比作常见的SQL:
select fld1, fld2 from tbl where 1=1 and fld1 > 8
在这种情况下, where 1=1
只是为了使您不必在第一个子句之前and
之后的每个子句之前放置一个where
。 您可以依赖于已存在的位置,并且只使用您添加的所有内容。
有些人可能会认为这是懒惰的,他们是对的,但这不一定是坏事:-)
任何体面的DBMS查询优化器都应该能够在转到数据库表之前去掉像这样的常量子句。
像其他人一样,逗号不是必需的。 但它在C99中是新的(在C89中是不允许的)并且也将在下一版本的C ++中被允许。
另一个理由是在“长度”枚举器和普通枚举器之间做出改变:
enum Items { A, B, C, LENGTH };
现在,您可以在编码指南中加入枚举中的最后一项应该使用逗号,但如果它是“长度”项目则不会 – 这只是告诉它有多少项目。
它还有助于自动生成项目(使用宏/预处理器),就像其他答案一样。
在标准C89中,不允许使用最后一个逗号。 完全停止。
允许它是一个共同的延伸; 特别是,它得到了海湾合作委员会的支持,但该标准明确禁止它。
在标准C99中,允许使用最后一个逗号,以便与数组和结构初始化器对称,它始终允许在最后一项上使用尾随逗号。
6.7.2.2枚举说明符
句法
enum-specifier: enum identifieropt { enumerator-list } enum identifieropt { enumerator-list , } enum identifier
允许尾随逗号的主要优点是它允许更容易的机器生成(C源代码) – 您不必为初始化列表中的最后一个(或可能是第一个)项编写特殊的大小写代码。 因此,像Yacc和Lex这样的程序,仅举两个,可以稍微简单一些。
不,不是必需的。 原因是,如果您不需要担心逗号是否存在,它可以更容易地实现剪切和粘贴代码的目的。
不,它不是必需的 – 实际上我会说它有不好的风格。
如前所述,这不是必需的。 支持尾随逗号的原因是它(假设项目一行排列)它允许您使用剪切/粘贴或拖放方便地重新排列枚举中项目的顺序,它还允许您注释掉最后一项而不产生语法错误。 省略尾随逗号是合法的,但会失去这些代码维护优势。
我忘记了,但尼克是对的。 我也使用了编译器指令的尾随逗号。 没有它,条件代码将变得更加混乱和难以阅读。
如果您使用宏,例如,它是可选且有用的
#ifdef _FLAG #define OPTS opt_four, opt_five, #else #define OPTS // none #endif enum { opt_one, opt_two, opt_three, OPTS };
最后一个尾随逗号不是必需的。
我更喜欢尾随逗号有两个原因:
- 清洁git差异 。
- 使用基于行的命令在编辑器中轻松编辑(例如Vim的
dd
)。
不,它不是必需的,应该省略代码清晰度。 它的存在/不存在没有效果。
它不是必需的,事实上一些编译器会抱怨你添加一个。 例如Visual Studio 6。
逗号的一个用途是使用c宏创建枚举。
#define ELEMENT(x) x, enum MyElements { ELEMENT(a) ELEMENT(b) ELEMENT(c) };
如果您需要对元素执行多项操作并且只想定义一次,则此模式非常有用。 有关此更完整的示例,您可以查看libiconv和iconv实用程序的代码。
其他答案提到它,但我只是想强调,在符合标准的C89和C ++中不允许使用尾随逗号,这使得旧版或不常见的编译器成为可移植性问题。 这是解释此问题和许多其他C / C ++问题的有用链接: http : //david.tribble.com/text/cdiffs.htm#C99-enum-decl
enum
定义或数组初始值设定项中的尾部是可选的,但非常有用,尤其是在跨越多行的列表中。 由于C99因为对称性而允许它,因为它为每个项目提供了相同的结构:
enum DAY { MON = 1, TUE, WED, THU, FRI, SAT, SUN, };
它可以更容易地使用脚本生成数组内容,并避免容易出错的情况,即向数组添加额外元素但忘记添加逗号可能会被忽视:
const char *osnames[] = { "CP/M", "MS/DOS", "Windows" }
添加额外的项目:
const char *osnames[] = { "CP/M", "MS/DOS", "Windows" "Linux", "OS/X" };
请注意列表中间缺少的逗号:编译器将第三个字符串解析为"WindowsLinux"
并且该错误不会生成语法错误。
通过尾随,
在每一行上,添加和删除项目更容易,而无需修改其他行。 如果有条件地编译行,则更有用,如下例所示:
const char *osnames[] = { "CP/M", "MS/DOS", "Windows", #ifdef __UNIX__ "Linux", "OS/X", #endif };