1

I've been learning C on learn-c.org

After covering the unit regarding typedef declarations and structs. They finished with what they called "a recursive definition of a linked list" I found fairly straightforward, except for what seems like a mismatched pointer....

typedef struct node{
    int val;
    struct node* next;
}node_t

// usage

node_t* head = NULL;
head = (node_t*) malloc(sizeof(node_t));
head->val = 1;
head->next = (node_t*) malloc(sizeof(node_t));
head->next->val = 2;
head->next->next = (node_t*) malloc(sizeof(node_t));
head->next->next->val = 3;

My understanding is, by supplying typedef struct node, we are able to declare the node pointer next within the structure.

My confusion occurs on line 11. We are dynamically allocating memory for our next node, but we cast the void pointer as a node_t pointer, not a node pointer -- despite that fact that head->next is a (node*) type. Why is this allowed? Is C simply just recasting to a (node*) behind the scenes, and (node_t*) is used for readability?

Barmar
  • 741,623
  • 53
  • 500
  • 612
sh34v3
  • 301
  • 2
  • 9

1 Answers1

5

The typedef makes node_t equivalent to struct node, so anywhere you might use struct node you can use the shorter node_t instead. So (node_t*) is equivalent to (struct node*).

The one exception is inside the structure declaration itself, because the name being defined isn't usable until after the typedef statement (just as you can't use a function or variable before they're declared).

BTW, it's not necessary to cast the result of malloc(). It returns void*, and C allows this to be assigned to any pointer type without an explicit cast. See Do I cast the result of malloc?

Remy Lebeau
  • 555,201
  • 31
  • 458
  • 770
Barmar
  • 741,623
  • 53
  • 500
  • 612
  • To your knowledge, is a canonical stance for typecasting void*; or does it really come down to personal preference? – sh34v3 Aug 09 '22 at 23:59
  • 1
    Most of the experts here recommend against it, for the reasons given in the question I linked to. – Barmar Aug 10 '22 at 00:00