简体   繁体   中英

I'm confused on why this Linked List implementation works

I've just recently gotten into linked lists and I'm adding my own "add to end" function.

void insert_at_end(Node** head, Node* node)
{
    Node* temp;

    temp = *head;

    if (temp == NULL) // linked list is empty
    {
        *head = node;
    }
    else
    {
        while (temp->pNext != NULL)
        {
            temp = temp->pNext;
        }
    temp->pNext = node;
    }
}

Originally I was doing temp != NULL instead of temp->pNext != NULL because I thought that way it would take me to the very LAST node, since it stops looping when temp still has data before it reaches NULL. Wouldn't temp->pNext != NULL stop at the 2nd to last node? Since it stops looping when it realizes that the last nodes next pointer is NULL, it does not travel to that node?

Thanks guys, If I need to clear anything up from that word vomit let me know.

Wouldn't temp->pNext != NULL stop at the 2nd to last node?

No. Here is the pictorial representation for ease of understanding.

With temp != NULL , temp will be pointing to NULL :

 +---+    +---+    +---+
 | 1 |--->| 2 |--->| 3 |---> NULL
 +---+    +---+    +---+      ^
                              |
                             temp

As you see temp is iterating until it becomes NULL , at which point you cannot attach anything to the final node because you're past it.


With temp->pNext != NULL , temp will be pointing to last node.

 +---+    +---+    +---+
 | 1 |--->| 2 |--->| 3 |---> NULL
 +---+    +---+    +---+
                     ^
                     |
                    temp

Here temp will iterate till its next node is NULL . That means you're pointing to the final node and you can use that pointer to adjust that node to point to a new one with temp->pNext = node :

 +---+    +---+    +---+    +---+
 | 1 |--->| 2 |--->| 3 |--->| 4 |---> NULL
 +---+    +---+    +---+    +---+
                     ^
                     |
                    temp

As an aside, you may also want to add the extra safety of ensuring the node you're given points to NULL , on the off chance the caller may forget to do that. That's as simple as adding this line to the start of the function:

node->pNext = NULL;

Let's make some analogy.

  • Each node is a station.
  • NULL is your stop station.
  • while (temp->pNext != NULL) { temp = temp->pNext; } while (temp->pNext != NULL) { temp = temp->pNext; } means drive and visit each station until reach the stop station.
  • When you reach the stop station, an additional station is needed to be added by temp->pNext = node;

Now the former stop station followed by the new added stop station(implicitly the new NULL ) is not a stop station, but the penultimate station to be visited.

have a reference for simple linked list concept

let us take an example

consider

struct node          
{
  int data;// data which you want to feed.
  struct node *next;// gona hold the address of the next data, so that link can be established
}*root,*p; // root is the starting reference to your linked list

case 1: you dont insert any element and your linked list is empty. Now when you insert a new data 10.it will check for any data in the global pointer reference to your linked list, if, the pointer seems to be NULL, then it means your liked list is empty.The memory stack will be created like this.

10

1000

10 is the data, 1000 is its address.

case 2: adding an element at its back.you want to add, data 20 to your linked list.you will be looking whether the linked list is empty or not first, using your global linked list address reference(it will be a pointer variable, holding your linked list 1st address, as per your code)

now when we see root->data is not null 1000->data is 10

we go for root->next which is null, which we come to know that this is the last node. 1000->next is NULL

and we insert the new node address to the root->next so that a link is created to the newly inserted node.

stack will be created like this

10 20

1000 1004

case3: now you want to add another data say 30 to the end of list again. just follow the same as case 2.

check for the node which is currently null, ie root->next == NULL, for this you use a loop to find the node which is currently in last, like this.

 struct node *temp; // creating a temp node which will be the new node we will insert
 temp = (struct node *)malloc(sizeof(struct node));// allocating the size for the temp node, same as the size of previous nodes.
 p = root;// i am giving my starting address to pointer p, i traverse the node with pointer p only, since i dont want to loose my root starting address.
 while(p->next != NULL)// checking for the last node
    p = p->next;// if last node not found, just move to next node, and see whether it is last node or not
 p->next = temp;// if last node is found, put the address of newly created temp node to the node previously found last in the linked list.
 temp->data = element;// feeding data to the temp node.
 temp->next = NULL;// keeping temp node as last, it is necessary to say temp wont has any more node connected.

NOTE dont think this is just a temp node, and will disappear once we come out of function, it is playing with pointer, so it wont destroyed until, the owner wont destroy it.

flow will be

newly created temp address is 1008

1000->next is 1004

1004->next is NULL

so, 1004->next will hold 1008 now

then,1008->data will be 30

then, 1008->next will be NULL

stack will be created like this

10 20 30

1000 1004 1008

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM