Значения перечисления по умолчанию в C одинаковы для всех компиляторов?

107

При объявлении перечисления , как показано ниже, не все компиляторы C установить значения по умолчанию , как x=0, y=1и z=2в обеих системах Linux и Windows?

typedef enum {
    x,
    y,
    z
} someName;
SSS
источник
3
Да, это требуется стандартами, и я уверен, что кто-то сможет их процитировать.
Nemo

Ответы:

115

Да. Если вы не укажете иное в определении перечисления, начальный перечислитель всегда имеет нулевое значение, а значение каждого последующего перечислителя на единицу больше, чем значение предыдущего перечислителя.

Джеймс МакНеллис
источник
14
и это идентичное поведение требуется как для C, так и для C ++. В C ++ это [dcl.enum]: «Если первый перечислитель не имеет инициализатора, значение соответствующей константы равно нулю. Определение перечислителя без инициализатора дает перечислителю значение, полученное путем увеличения значения предыдущего перечислителя на единицу».
Ben Voigt
3
Да, а также другие языки, начинающиеся с буквы C, например C #.
Джеймс МакНеллис
70

C99 Стандартный

В проекте N1265 C99 говорится в 6.7.2.2/3 «Спецификаторы перечисления».

Перечислитель со знаком = определяет свою константу перечисления как значение константного выражения. Если у первого перечислителя нет =, значение его константы перечисления равно 0. Каждый последующий перечислитель с no = определяет свою константу перечисления как значение константного выражения, полученного добавлением 1 к значению предыдущей константы перечисления. (Использование перечислителей с = может создавать константы перечисления со значениями, которые дублируют другие значения в том же перечислении.)

Таким образом, следующие реализации всегда соответствуют соответствующим реализациям:

main.c

#include <assert.h>
#include <limits.h>

enum E {
    E0,
    E1,
    E2 = 3,
    E3 = 3,
    E4,
    E5 = INT_MAX,
#if 0
    /* error: overflow in enumeration values */
    E6,
#endif
};

int main(void) {
    /* If unspecified, the first is 0. */
    assert(E0 == 0);
    assert(E1 == 1);
    /* Repeated number, no problem. */
    assert(E2 == 3);
    assert(E3 == 3);
    /* Continue from the last one. */
    assert(E4 == 4);
    assert(E5 == INT_MAX);
    return 0;
}

Скомпилируйте и запустите:

gcc -std=c99 -Wall -Wextra -pedantic -o main.out main.c
./main.out

Протестировано в Ubuntu 16.04, GCC 6.4.0.

Чиро Сантилли 郝海东 冠状 病 六四 事件 法轮功
источник
7

Если первое значение переменной enum не инициализировано, компилятор C автоматически присваивает значение 0. Компилятор продолжает увеличивать значение предыдущей переменной enum на 1.

Например:

enum months{jan,feb,mar}

Объяснение: Значение jan будет 0, feb будет 1, mar будет 2.

enum months{jan=123,feb=999,mar}

Пояснение: Значение jan будет 123, feb будет 999, mar будет 1000.

enum months{jan='a',feb='s',mar}

Пояснение: Значение jan будет 'a', feb будет 's', mar будет 't'.

Виньеш вики
источник
1
mar 't'не гарантируется, могут быть наборы символов, в которых буквы не расположены в последовательном алфавитном порядке
MM
-15

Да, значение enum по умолчанию начинается с 0 по n элемент любой платформы.

Девидас Гайквад
источник
14
Подумайте, как ваш ответ пополнит список ответов. То есть, как ваш новый ответ (5 лет спустя) добавляет что-то новое, чего нет в другом ответе? На первый взгляд, он менее информативен, чем два других ответа.
LawfulEvil 02
2
Эххх @LawfulEvil, расслабься. Множественные ответы дают людям, которые смотрят на это в будущем, несколько точек зрения. Тем не менее, это плохо отформатированный, неинформативный ответ, но достаточные ответы сами по себе неплохи.
Кенни Уорден,