Using the struct keyword we can create complex data structures using basic C types.

A structure is a collection of values of different types. Arrays in C are limited to a type, so structures can prove to be very interesting in a lot of use cases.

This is the syntax of a structure:

struct <structname> {
//...variables
};

Example:

struct person {
int age;
char *name;
};

You can declare variables that have as type that structure by adding them after the closing curly bracket, before the semicolon, like this:

struct person {
int age;
char *name;
} flavio;

Or multiple ones, like this:

struct person {
int age;
char *name;
} flavio, people[20];

In this case I declare a single person variable named flavio, and an array of 20 person named people.

We can also declare variables later on, using this syntax:

struct person {
int age;
char *name;
};

struct person flavio;

We can initialize a structure at declaration time:

struct person {
int age;
char *name;
};

struct person flavio = { 37, "Flavio" };

and once we have a structure defined, we can access the values in it using a dot:

struct person {
int age;
char *name;
};

struct person flavio = { 37, "Flavio" };
printf("%s, age %u", flavio.name, flavio.age);

We can also change the values using the dot syntax:

struct person {
int age;
char *name;
};

struct person flavio = { 37, "Flavio" };

flavio.age = 38;

Structures are very useful because we can pass them around as function parameters, or return values, embedding various variables within them, and each variable has a label.

It’s important to note that structures are passed by copy, unless of course you pass a pointer to a struct, in which case it’s passed by reference.

Using typedef we can simplify the code when working with structures.

Let’s make an example:

typedef struct {
int age;
char *name;
} PERSON;

The structure we create using typedef is usually, by convention, uppercase.

Now we can declare new PERSON variables like this:

PERSON flavio;

and we can initialize them at declaration in this way:

PERSON flavio = { 37, "Flavio" };