Accessing variables from a struct

0

I'm studying C and I'm doubtful about the difference of the following lines:

(*depois).agora = 20

and

*depois.agora = 20;

So I understood the point . has priority and the compiler would try to solve depois.agora and after that it would solve *(depois.agora)

Then, depois is the memory address. if I tried to access *(depois.agora) , would not I be getting the value that is contained in the address depois.agora ?

What would be the difference between the 2 lines?

#include <stdio.h>

struct horario
{
    int hora;
    int minuto;
    int segundo;
};

int main(void)
{
    struct horario agora;
    struct horario *depois;

    depois = &agora; // depois aponta para agora, ou seja, armazena o endereco de memoria de agora

    (*depois).agora = 20; // "atalho": depois->agora = 20

    *depois.agora = 20; // errado, por quê?

    // * = operador de derreferência
    return 0;
}
    
asked by anonymous 08.10.2017 / 18:37

2 answers

1

I start by saying that you are accessing the incorrect value in the structure at:

(*depois).agora = 20; 
*depois.agora = 20;

Because the horario structure does not have the agora field, so you would have to switch to one of its fields, such as hora :

(*depois).hora = 20; 
*depois.hora = 20;

However, the problem has to do with operator precedence. The . operator has priority over the * operator. To make it more obvious we could rewrite the instructions according to the precedence of the operators:

(*depois).hora = 20; 
*(depois.hora) = 20;

Responding to the question now, depois is a pointer that points to a structure. So first you have to go to the memory location where the structure is doing *depois , and only when you have accessed the location in memory will the bytes needed to reach the hora field with .hora which gives you the first case you specified:

(*depois).hora = 20;

If you do not put the parentheses, by the precedence of the operators first is done depois.hora that will try to access the pointer as if it were a structure, which by itself fails because it is a pointer and not a structure. The compiler soon realizes by the types that it is wrong and immediately gives a compilation error:

  

error: request for member 'time' in something not a structure or   union

Reading carefully we see that the compiler indicates that we are accessing a hora field of something that is not a structure or union (it's actually a pointer). Note also that only depois.hora is sufficient to generate the error.

Operator Precedence Table

    
08.10.2017 / 19:47
2

Essentially understood everything.

The first one is getting the value that is in the address depois and then taking the field hora (in the question the field name is wrong). The parentheses are just there to indicate that first comes the reference that will produce an object of type struct horario which in turn has a field hora .

The second, by operator precedence, is taking the depois pointer and trying to access the hora field in it, it happens that a pointer has no fields, it is an address and nothing else, so it already gives error. He will not even try to use the dereference operator in something that does not make sense. It's like this:

*(depois.agora) = 20;

You can only access an object in a way compatible with its contents.

    
08.10.2017 / 19:46