Reputation: 11
I'm currently having problems with a linked list I am creating. Basically what is happening is when I free the head node inside a function it works in the function itself. But when I try to access my linked list from my main function I access the recently freed head but with only one of its payload freed.
Here are snippets of my code:
struct item
{
UINT time ;
UINT id ;
UINT event ;
struct item *next ;
};
This is my struct of my nodes which contain 3 different payload. This is my initialization. Take note I've manually initialized 3 nodes for practice:
struct item *head=NULL, *tail=NULL, *trail=NULL, *end=NULL;
head=malloc(sizeof(struct item));
trail=head;
trail->next=NULL;
//TEST
{
head=malloc(sizeof(struct item));
trail=head;
trail->next=NULL;
head->time=50;
head->event=100;
head->id=1989;
//printf("head->time: %d\nhead->event: %d\nhead->id: %d\n",head->time, head->event, head->id);
//printf("trail->time: %d\ntrail->event: %d\ntrail->id: %d\n",trail->time, trail->event, trail->id);
//this line of code produces a single payload in the linked list
tail=malloc(sizeof(struct item));
trail->next=tail;
tail->time=1;
tail->event=2;
tail->id=3;
trail=tail;
//up until here
/*
tail=malloc(sizeof(struct item));
trail->next=tail;
trail=tail;
// three lines of code needed to create a linked list
*/
//this is linked to the code above
tail=malloc(sizeof(struct item));
trail->next=tail;
tail->time=5;
tail->event=7;
tail->id=60;
trail=tail;
trail->next=NULL;
end=trail;//end of the linked list
//printf("tail->time: %d\ntail->event: %d\ntail->id: %d\n\n\n",tail->time, tail->event, tail->id);
//this code prints out the entire linked list
trail=head;
do
{
TEST printf("trail->time: %d\ntrail->event: %d\ntrail->id: %d\n\n",trail->time, trail->event, trail->id);
trail=trail->next;
}
while(trail!=NULL);
}
//creation of linked list complete
//test to traverse the linked list
Ignore the comments I've recently just started doing linked list a couple of hours ago. Now here's my problem. When I delete the head of the linked list using free inside a function it frees it indeed but when I traverse my linked list in the main function it will output 3 nodes. This is the line of code I use to traverse my linked list in the main function:
trail=head;
int item=0;
do
{
item++;
printf("item %d = %d %d %d\n",item ,trail->time, trail->id, trail->event);
trail=trail->next;
}
while(trail!=NULL);
And here is the function I use to delete my head:
void list_head_delete(struct item *head)
{
struct item *trail;
trail=head;
trail=trail->next;
free(head);
head=trail;
}
When traversing my linked list it will normally output this:
item 1 = 50 1989 100
item 2 = 1 3 2
item 3 = 5 60 7
If I call my function to delete the head and traverse the linked list again I will get this output:
item 1 = 0 1989 100
item 2 = 1 3 2
item 3 = 5 60 7
Upvotes: 1
Views: 279
Reputation: 59617
Your delete function signature is: void list_head_delete(struct item *head)
. Using this signature, you pass a pointer to the head
node, and so you can change the struct node
that the pointer references, but you can't change the pointer itself. In C, function arguments are pass-by-value, so the actual pointer that you pass is only a copy, and changes to it, e.g. head=trail;
, will only be to the copy of the pointer in the function. When the function returns, head
will contain it's original address, which now references freed memory.
If you want to change what the head pointer points to, then you'll need to pass a pointer to the pointer:
void list_head_delete(struct item **head);
You'll need to change your delete function to deal with this extra level of reference when using the head
argument.
Alternately, you can pass back the new list as the function return value:
struct node *list_head_delete(struct item *head);
// ... and to use it:
head = list_head_delete(head);
Upvotes: 3