我想 typdef 一个枚举,它是另一个 typdef 枚举的扩展。
一个 typedef enum 有 4 个元素(因为我在结构中只有 2 位来存储它的值),另一个有相同的 4 个元素,加上第 5 个元素(不存储在结构中,只用于标记无效值)。
示例代码:
typedef enum {
case0,
case1,
case2,
case3,
} case_t;
typedef enum {
one_t, // 0 through 3 <---HOW CAN I DO THIS?
invalid_case, // 4
} case_ext_t
struct {
case_t case_ :2; // 2 bits, for up to 4 cases
unsigned other_stuff:14; //
} a_word;
case_ext_t my_case = invalid_case;
if (condition) {
my_case = case2;
}
if (my_case != invalid_case) {
switch (my_case) {
case case0: {....} break;
case case1: {....} break;
case case2: {....} break;
case case3: {....} break;
}
}
我能否键入一个包含 case_t 的所有元素以及其他元素的 case_ext_t?
或者,我可以只定义更大的 typedef 枚举 case_ext_t,但在存储它的 2 位结构时只使用它的前 4 个元素吗?
最佳答案
Can I typedef a case_ext_t that includes all the elements of case_t, plus additional ones?
不,你不能。如果标识符在给定的翻译单元中被声明为枚举常量,那么它必须是该标识符在翻译单元中的唯一声明 (C2011, 6.7/5)。因此,如果两个枚举类型在同一个翻译单元中使用,除了作为不完整类型之外,那么它们不能有任何共同的枚举常量。
Alternatively, can I define just the larger typedef enum case_ext_t, yet use only its first 4 elements when storing it 2 bits of a struct?
没有。位域声明不能指定比字段的基本类型实际具有的位更多的位 (C2011, 6.7.2.1/4)。此外,无论指定的位数是多少,是否可以使用枚举类型作为位字段的声明类型都是实现定义的;保证允许的唯一类型是 _Bool
、signed int
和 unsigned int
(C2011, 6.7.2.1/5)。
我认为最好的办法是将位域声明为 unsigned int
类型,并且只声明较大的枚举类型:
typedef enum {
case0,
case1,
case2,
case3,
invalid_case, // 4
} case_t;
struct {
unsigned case_:2;
unsigned other_stuff:14;
} a_word;
对 invalid_case
使用适当的测试来保护对 a_word.case_
的赋值。
或者,您真的需要使用位域吗?这似乎引起了您的极大惊愕,而且还不清楚这个麻烦是否值得。为什么不简单地使用
struct {
case_t case_;
unsigned other_stuff;
} a_word;
?
关于我可以 typedef 一个枚举,它是另一个 typedef 枚举的扩展吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/40822988/