The following shows that enums can take on different types depending on what is in the enumeration list. If all values are positive then the type of the enum is unsigned int. If one of the values is negative the type is signed int.
/* stack exchange sample code for signed & unsigned enums */
#define _GNU_SOURCE 1
#include <stdio.h>
#include <assert.h>
int main ( int argc, char *argv[] ) {
enum color_ek {red=0, org, yel, grn, blu, ind, vio} color;
enum COLOR_ek {RED=0, ORG, YEL, GRN, BLU, IND, VIO, BLK=-100} COLOR;
/* Signed count DOWN to red works OK. */
printf("Counting signed COLOR down from VIO to RED: ");
for (COLOR=VIO; RED<=COLOR ; COLOR-- ) {
printf("%d, ",COLOR);
assert( RED <= COLOR && COLOR <= VIO );
}
printf("\nCOLOR DOWNTO RED loop DONE. On exit COLOR=%d \n",COLOR);
/* Unsigned count DOWN to org works OK. */
printf("Counting unsigned color down from vio to org: ");
for (color=vio; org<=color ; color-- ) {
printf("%d, ",color);
assert( org <= color && color <= vio );
}
printf("\ncolor DOWNTO org loop DONE. On exit color=%d \n",color);
/* Unsigned count DOWN to red does not work */
printf("Counting unsigned color down from vio to red: ");
fflush(stdout);
for (color=vio; color>=red ; color--) {
printf("%d, ",color);
fflush(stdout);
assert(red <= color && color <= vio );
}
printf("color DOWNTO red loop DONE.On exit color=%d \n",color);
return 0 ;
} /* end main */
> /*
> The result of the above is:
>
> scratchpad$ gcc enum_stackexg.c && ./a.out
> Counting signed COLOR down from VIO to RED: 6, 5, 4, 3, 2, 1, 0,
> COLOR DOWNTO RED loop DONE. On exit COLOR=-1
> Counting unsigned color down from vio to org: 6, 5, 4, 3, 2, 1,
> color DOWNTO org loop DONE. On exit color=0
> Counting unsigned color down from vio to red: 6, 5, 4, 3, 2, 1, 0, -1,
> a.out: enum_stackexg.c:34: main: Assertion `red <= color && color <= vio' failed.
> Aborted (core dumped)
>
> */