Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How do I use typedef and typedef enum in C?

Tags:

c

typedef

Consider:

#define MAXROW 20 #define MAXCOL 60 typedef State Grid[MAXROW+2] [MAXCOL+2] typedef enum state {DEAD,ALIVE} State 

How do I use typedef and typedef enum in C? What does this part of the code do?

like image 671
user39555 Avatar asked Dec 06 '13 14:12

user39555


People also ask

Can we use typedef with enum in C?

An introduction to C Enumerated TypesUsing the typedef and enum keywords we can define a type that can have either one value or another. It's one of the most important uses of the typedef keyword. This is the syntax of an enumerated type: typedef enum { //...

What is typedef and enum in C?

A typedef is a mechanism for declaring an alternative name for a type. An enumerated type is an integer type with an associated set of symbolic constants representing the valid values of that type.

How does enum is different from typedef in C?

enum defines a type name automatically, While in case of typedef we define a new data type which may be of any kind of data type so that we do not have declare it explicitly everytime.

How do we use typedef in C?

The typedef is a keyword used in C programming to provide some meaningful names to the already existing variable in the C program. It behaves similarly as we define the alias for the commands. In short, we can say that this keyword is used to redefine the name of an already existing variable.


1 Answers

typedef enum state {DEAD,ALIVE} State; |     | |                     | |   |^ terminating semicolon, required!  |     | |   type specifier    | |   | |     | |                     | ^^^^^  declarator (simple name) |     | |                     |     |     | ^^^^^^^^^^^^^^^^^^^^^^^   |     | ^^^^^^^-- storage class specifier (in this case typedef) 

The typedef keyword is a pseudo-storage-class specifier. Syntactically, it is used in the same place where a storage class specifier like extern or static is used. It doesn't have anything to do with storage. It means that the declaration doesn't introduce the existence of named objects, but rather, it introduces names which are type aliases.

After the above declaration, the State identifier becomes an alias for the type enum state {DEAD,ALIVE}. The declaration also provides that type itself. However that isn't typedef doing it. Any declaration in which enum state {DEAD,ALIVE} appears as a type specifier introduces that type into the scope:

enum state {DEAD, ALIVE} stateVariable; 

If enum state has previously been introduced the typedef has to be written like this:

typedef enum state State; 

otherwise the enum is being redefined, which is an error.

Like other declarations (except function parameter declarations), the typedef declaration can have multiple declarators, separated by a comma. Moreover, they can be derived declarators, not only simple names:

typedef unsigned long ulong, *ulongptr; |     | |           | |  1 | |   2   | |     | |           | |    | ^^^^^^^^^--- "pointer to" declarator |     | |           | ^^^^^^------------- simple declarator |     | ^^^^^^^^^^^^^-------------------- specifier-qualifier list ^^^^^^^---------------------------------- storage class specifier 

This typedef introduces two type names ulong and ulongptr, based on the unsigned long type given in the specifier-qualifier list. ulong is just a straight alias for that type. ulongptr is declared as a pointer to unsigned long, thanks to the * syntax, which in this role is a kind of type construction operator which deliberately mimics the unary * for pointer dereferencing used in expressions. In other words ulongptr is an alias for the "pointer to unsigned long" type.

Alias means that ulongptr is not a distinct type from unsigned long *. This is valid code, requiring no diagnostic:

unsigned long *p = 0; ulongptr q = p; 

The variables q and p have exactly the same type.

The aliasing of typedef isn't textual. For instance if user_id_t is a typedef name for the type int, we may not simply do this:

unsigned user_id_t uid;  // error! programmer hoped for "unsigned int uid".  

This is an invalid type specifier list, combining unsigned with a typedef name. The above can be done using the C preprocessor:

#define user_id_t int unsigned user_id_t uid; 

whereby user_id_t is macro-expanded to the token int prior to syntax analysis and translation. While this may seem like an advantage, it is a false one; avoid this in new programs.

Among the disadvantages that it doesn't work well for derived types:

 #define silly_macro int *   silly_macro not, what, you, think; 

This declaration doesn't declare what, you and think as being of type "pointer to int" because the macro-expansion is:

 int * not, what, you, think; 

The type specifier is int, and the declarators are *not, what, you and think. So not has the expected pointer type, but the remaining identifiers do not.

And that's probably 99% of everything about typedef and type aliasing in C.

like image 123
Kaz Avatar answered Oct 10 '22 00:10

Kaz