The difference is on this line:
typedef Node *No;
When you wear one typedef
is saying that you want a name to represent some other existing definition that is placed just before the name.
So in this example the name No
it’s actually the same as Node *
, or more precisely struct Node *
since Node
is in the same namespace there did not need to put the specification.
So when you write:
int push2(No *li, int data)
It’s actually the same as writing:
int push2(struct Node **li, int data)
So it equals to:
void push1(struct Node **headRef, int data)
This code better shows the difference between transmitting the result obtained within the function by a parameter that is passed as reference or returned at the end of the function execution. In practice the result is the same but the form is different, which uses the return
there will be a copy, which may be good or bad according to the context:
#include <stdio.h>
#include <stdlib.h>
struct Node {
int data;
struct Node *next;
};
typedef struct Node *No;
typedef struct Node Elem;
void push1(struct Node** headRef, int data) {
struct Node* newNode = malloc(sizeof(struct Node));
newNode->data = data;
newNode->next = *headRef;
*headRef = newNode;
}
No *push2(No *li, int data) {
Elem *no = malloc(sizeof(Elem));
no->data = data;
no->next = (*li);
*li = no;
return li;
}
int main() {
int arr[] = {1, 2, 3};
int i = 0;
struct Node *head = NULL;
push1(&head, arr[i]);
printf("%d", head->data);
No *li = malloc(sizeof(No));
No *result = push2(li, arr[i]);
printf("%d", (*li)->data);
printf("%d", (*result)->data);
}
Behold working in the ideone. And in the repl it.. Also put on the Github for future reference.