枚举C编程中用户定义的数据类型

枚举C编程中用户定义的数据类型,c,enums,C,Enums,我正在研究enum,即C中的关键字,用于定义枚举数列表,也称为枚举常量,编译器为其分配有符号整数值 Syntax: enum identifier (optional) { enumerator-list } 我在玩enum来了解编译器是如何将整数分配给枚举列表中的枚举常量的 因此,当我使用下面的enum编写3个不同的程序时,我产生了一些问题,这些问题附在下面的每个程序中 计划-1 #include<stdio.h> #include<inttypes.h> enum

我正在研究
enum
,即
C
中的关键字,用于定义枚举数列表,也称为枚举常量,编译器为其分配有符号整数值

Syntax:
enum identifier (optional) { enumerator-list }
我在玩
enum
来了解编译器是如何将整数分配给枚举列表中的枚举常量的

因此,当我使用下面的
enum
编写3个不同的程序时,我产生了一些问题,这些问题附在下面的每个程序中

计划-1

#include<stdio.h>
#include<inttypes.h>

enum days_of_week {Sunday, Monday, Tuesday, Wednesday, Thursday, Friday, Saturday};

int main(void) {
    printf("%u %u %u %u %u %u %u\n", Sunday, Monday, Tuesday, Wednesday, Thursday, Friday, Saturday);
    return 0;
}
输出:0 1 65535 65536 65537 65538 65539
,在此之前,我已将
UINT16_MAX
分配给
星期二
,编译器根据
基于零的索引将整数分配给枚举常量
,并在
星期二之后,根据分配给先前枚举常量+1的整数将整数分配给枚举常量

计划-3

#include<stdio.h>
#include<inttypes.h>

enum days_of_week {Sunday, Monday, Tuesday = UINT32_MAX, Wednesday, Thursday, Friday, Saturday};

int main(void) {
    printf("%u %u %u %u %u %u %u\n", Sunday, Monday, Tuesday, Wednesday, Thursday, Friday, Saturday);
    return 0;
}

  • 由此,我推断出我可以分配给这些枚举常量的最大整数是
    UINT16_MAX
    ,但我有一个问题,这个值与编译器/系统有关吗

  • 编译器在哪一步将这些整数值分配给这些枚举数,我的意思是编译器是在编译时还是在运行时分配这些值

与宏相比,使用
enum
的优点是:

  • 它增加了源代码的可读性
  • 作用域规则适用于
    枚举
    ,但不适用于宏
  • 它将有符号整数自动初始化为枚举器列表中的枚举器

除了上面列出的优点外,使用
enum
还有哪些优点,此外,与宏相比,使用
enum
更可取的用例是什么?

我修改了程序1以突出显示如何使
enum
本地数组一起工作的更具体编程技术,如下所示:

#include <stdio.h>
#include <string.h>
#include <inttypes.h>

enum days_of_week {Sunday = 3488, Monday, Tuesday, Wednesday, Thursday, Friday, Saturday};

const char *getDayOfWeek(unsigned int day);
const char *getDayOfWeek(unsigned int day) {
    static const char *days[7] = {
        "Sunday",
        "Monday",
        "Tuesday",
        "Wednesday",
        "Thursday",
        "Friday",
        "Saturday"
    };
    day -= 3488;
    day %= 7;
    return days[day];
}

int main(void);
int main() {
    static unsigned int day = (unsigned int) Thursday;

    printf("%X %X %X %X %X %X %X\n", Sunday, Monday, Tuesday, Wednesday, Thursday, Friday, Saturday);

    if (day >= Sunday && day <= Saturday) {
        printf("The day of week is: %s (or %X).\n", getDayOfWeek(day), day);
    }

    return 0;
}
#包括
#包括
#包括
每周的枚举天数{Sunday=3488,星期一、星期二、星期三、星期四、星期五、星期六};
常量字符*getDayOfWeek(未签名的整数天);
常量字符*getDayOfWeek(未签名整数天){
静态常量字符*天[7]={
“星期日”,
“星期一”,
“星期二”,
“星期三”,
“星期四”,
“星期五”,
“星期六”
};
日-=3488;
日百分比=7;
返回天数[天];
}
int main(无效);
int main(){
静态无符号整数日=(无符号整数)星期四;
printf(“%X%X%X%X%X%X%X%X\n”,周日、周一、周二、周三、周四、周五、周六);

如果(天>=星期日和(&D),错误不是将
UINT32_MAX
分配给
beday
,而是将
UINT32_MAX+1
分配给
beday
“编译器是在编译时还是在运行时分配这些值”-编译器本身仅在编译时存在,因此它决定在编译时分配什么值。在特定的编译器中,使用特定的标志,可以。标准()只要求“常量类型与char、有符号整数类型或无符号整数类型兼容”关于
C
中的
enum
有一个很好的解释/讨论。@不,在您的实现中,最大值是
INT32_MAX
,因为enum是有符号整数值。您应该使用
%d
(而不是
%u
)打印分配给枚举常量的值。1.这在问题中回答了什么?--2.如何确保枚举名称和字符串内容匹配?--3.为什么不减去
Sunday
,而不是在别处定义的幻数?因为这些是可打印部分的
十六进制字符单词'DAY'或'DA'加上'DA0'的数组索引'0'到'6'…'DA6'(参见,3488=DA0=“星期日”,3489=DA1=“星期一”,3490=DA2=“星期二”,3491=DA3=“星期三”,等等)。你只需要指定这个特定序列中的第一个数字。当你指十六进制时,不要写十进制数字。而且你没有回答我的任何问题。我有点理智,所以我对此表示歉意。如果你想的话,我可以重做代码来说明重点是什么。。。
enum_example_1.c:8:58: error: overflow in enumeration values
enum days_of_week {Sunday, Monday, Tuesday = UINT32_MAX, Wednesday, Thursday, Friday, Saturday};
#include <stdio.h>
#include <string.h>
#include <inttypes.h>

enum days_of_week {Sunday = 3488, Monday, Tuesday, Wednesday, Thursday, Friday, Saturday};

const char *getDayOfWeek(unsigned int day);
const char *getDayOfWeek(unsigned int day) {
    static const char *days[7] = {
        "Sunday",
        "Monday",
        "Tuesday",
        "Wednesday",
        "Thursday",
        "Friday",
        "Saturday"
    };
    day -= 3488;
    day %= 7;
    return days[day];
}

int main(void);
int main() {
    static unsigned int day = (unsigned int) Thursday;

    printf("%X %X %X %X %X %X %X\n", Sunday, Monday, Tuesday, Wednesday, Thursday, Friday, Saturday);

    if (day >= Sunday && day <= Saturday) {
        printf("The day of week is: %s (or %X).\n", getDayOfWeek(day), day);
    }

    return 0;
}