Structures and Pointers in C

A data structure, when passed as an argument to a function, is always passed by copy. In other words, a copy of the original structure is created, which is passed to the function.

In this lesson we will see how to pass structures by reference, that is, how to pass a pointer to the structure itself. We will also see how to declare and manipulate pointers to structures in C language.

Pointers and struct

A pointer can point to any data type, double, int, char, and it can also point to a struct data structure.

In this case, the syntax for declaring a pointer to a structure depends on whether we use a tagged struct or a type defined with typedef.

Let's take an example struct:

struct Point {
    int x;
    int y;
};

typedef struct Point PointType;

Declaring a pointer to a tagged struct Point is simple:

struct Point *pointPtr;

Declaring a pointer to a struct defined with typedef is equally simple:

PointType *pointPtr;
Definition

Pointers to Structures

A pointer in C language can also point to a struct data structure.

To define a pointer to a tagged struct structure, the following syntax is used:

struct StructureName *pointer;

To define a pointer to a structure defined with typedef, the following syntax is used:

StructureType *pointer;

For pointers to structures, all typical pointer operations are allowed:

  • Assignment of a memory address to a pointer;
  • Pointer arithmetic;
  • Assignment of one pointer to another.

What deserves a separate discussion concerns accessing the members of a structure through a pointer.

Arrow Operator

Let's take the following example:

struct Point {
    int x;
    int y;
};

struct Point point = { 10, 20 };

struct Point *point_ptr = &point;

the pointer point_ptr points to the structure point. It is a pointer in all respects, so we can apply the dereferencing operator * to it to access the pointed content:

*(point_ptr);

This will return the structure point itself. To access the members of the structure, we can use the . operator:

(*point_ptr).x = 30;
(*point_ptr).y = 40;

This syntax, however, is quite verbose.

Fortunately, in C there is a dedicated operator to access the members of a structure through a pointer: the arrow operator ->.

point_ptr->x = 30;
point_ptr->y = 40;

This code is equivalent to the one above, but much more readable.

In fact, the following equality always holds:

point_ptr->x == (*point_ptr).x
Definition

Arrow Operator ->

In C language, the arrow operator -> is used to access the members of a structure through a pointer.

The syntax is as follows:

struct structure_name {
    /* Fields */
};

struct structure_name structure;

struct structure_name *ptr;

ptr = &structure;

ptr->field = value;

The arrow operator is semantically equivalent to:

(*ptr).field = value;

Passing Structures to Functions by Reference

Now that we know how to declare and manipulate pointers to structures, we can study how to pass structures to functions by reference.

The mechanism is identical in all respects to the one used to pass any other data type by reference: we pass the pointer to the structure. We just need to remember to use the arrow operator to access the members of the structure.

Let's consider an example. Suppose we have a function that increments the coordinates of a point:

struct Point {
    double x;
    double y;
};

void incrementPoint(struct Point *point, double dx, double dy) {
    point->x += dx;
    point->y += dy;
}

We can call this function by passing a pointer to the Point structure:

struct Point point = { 10.0, 20.0 };

incrementPoint(&point, 5.0, 5.0);

After the call to incrementPoint, the structure point will have the coordinates (15.0, 25.0).

In this way, we can pass structures to functions by reference, avoiding copying the structure itself.

Definition

Passing Structures to Functions by Reference

To pass a structure to a function by reference, a pointer to the structure itself is passed and the members of the structure are accessed through the arrow operator ->.

void function(struct Structure *pointer) {
    pointer->field = value;
}

In Summary

In this lesson we have seen how to declare and manipulate pointers to structures in C language. We have learned to use the arrow operator -> to access the members of a structure through a pointer.

We have also studied how to pass structures to functions by reference, by passing a pointer to the structure itself.