enum hack在C中工作吗?如果是这样,它应该在VisualStudio 2003中工作吗?

enum hack在C中工作吗?如果是这样,它应该在VisualStudio 2003中工作吗?,c,visual-studio-2003,C,Visual Studio 2003,我讨厌你。为了从旧代码库中尽可能多地消除它们,我需要依赖于定义包含数组的结构。不幸的是,当C项目包含incriminated.h文件时,我无法编译它 typedef struct _P_O { enum { MAXELEMENTS=10 }; P_O_U elem; ULONG id[MAXELEMENTS]; USHORT nid; } P_O, *PP_O; 这会产生错误: “类型”:没有使用此类型定义的成员标识符解析为 类型名称位于聚合声明中,但编译器无法

我讨厌你。为了从旧代码库中尽可能多地消除它们,我需要依赖于定义包含数组的结构。不幸的是,当C项目包含incriminated.h文件时,我无法编译它

typedef struct _P_O {
    enum { MAXELEMENTS=10 };
    P_O_U elem;
    ULONG id[MAXELEMENTS];
    USHORT nid;
} P_O, *PP_O;
这会产生错误:

“类型”:没有使用此类型定义的成员
标识符解析为 类型名称位于聚合声明中,但编译器无法 宣布一名成员

OT:我讨厌使用10Y.o.的编译器,不得不保留旧的c代码和糟糕的设计;不仅仅是定义:)

像这样的enum hack在C中是有效的(但不是一种好的代码风格,请参见@Jonathan Leffler的评论)。因为当定义了
id
时,
MAXELEMENTS
符合枚举常量

C99 6.2.1标识符的范围

结构、联合和枚举标记的作用域在 声明标记的类型说明符中的标记每个枚举常量的作用域在其定义枚举器出现在枚举器列表中后立即开始。任何其他标识符的作用域在其声明器完成后立即开始

枚举是一种整型常量

C99 6.6常量表达式

整型常量表达式应为整型,且只能包含整型常量、枚举常量、字符常量、结果为整型常量的sizeof表达式的操作数,以及作为强制转换直接操作数的浮点常量。整数常量表达式中的强制转换运算符只能将算术类型转换为整数类型,除非作为操作数的一部分转换为sizeof运算符


最后,整数常量可以在数组声明符中使用,请参见C99 6.7.5.2数组声明符。这并不奇怪。

给定问题中的代码,GCC警告:
警告:声明不会为枚举行声明任何内容

将枚举放在结构之外,您就会没事了

typedef int P_O_U;
typedef unsigned long ULONG;
typedef unsigned short USHORT;

enum { MAXELEMENTS = 10 };

typedef struct _P_O
{
    P_O_U  elem;
    ULONG  id[MAXELEMENTS];
    USHORT nid;
} P_O, *PP_O;

您不能有两个名为
id
的元素…这是转录问题还是真正的问题?转录错误,谢谢!!!GCC警告:
警告:声明不会为
enum
行声明任何内容。把
enum
放在
struct
之外,你就没事了。@JonathanLeffler的答案为我编译。@JonathanLeffler你应该把你的评论作为回答你应该得到一个关于
声明没有声明任何东西的警告。它可能会编译,但不是没有警告……我更喜欢没有警告的代码。@JonathanLeffler我同意你的观点,编译时最好没有警告。但是,你看,这并不总是可能的(你对我面临的代码质量有一个大致的了解吗?)这里的问题是VS2003根本没有编译它。@JonathanLeffler我同意你的观点,我会选择不这样使用,但我确实认为它是有效的C,这是OP所要求的。ISO/IEC 9899:2011,§6.7.2.1结构和联合说明符的语法表明您可以编写
struct tag{int;double x;}(结构声明器列表是可选的)。然而,写这样一行会产生警告。
enum
行类似-它定义了一个类型,但没有向结构中添加成员,这是允许的,但(并非不合理地)会生成警告。所以是的,它是“合法的”C;编译器对此提出警告也是合理的。因为编译器确实会对此发出警告,而且无警告编译是可取的,所以不要使用这种表示法;它给你一个错误!:(这个解决方案的问题是MAXELEMENTS是全局的,如果我使用最初的define,它会是全局的。这个解决方案比#define MAXELEMENTS 10#有什么优势吗?@StefanoFalasca为什么不只是一个
const static
变量呢?所以你想要避免#define,你不需要或想要
MAXELEMENTS
的值>要在全球可见?为什么不直接转到
ULONG id[19]
然后?@user2485710 beause const静态变量是该语言的一个新添加项(“new”一词有相对的含义,你看?:)。它不存在于我的电脑上compiler@AShelly因为它需要被外部世界访问,这与它是全球性的不同。使用enum hack,以及使用上面建议的静态const变量(当然,这是正常人唯一会做的事情)可以让您通过_P_O::MAXELEMENTS访问该数字
typedef int P_O_U;
typedef unsigned long ULONG;
typedef unsigned short USHORT;

enum { MAXELEMENTS = 10 };

typedef struct _P_O
{
    P_O_U  elem;
    ULONG  id[MAXELEMENTS];
    USHORT nid;
} P_O, *PP_O;