Search code examples
cpointerslinked-listinsertcircular-list

Insertion at end in circular linked list not working in C


Please point out the error in the code.

The function insertatend() inserts for the first time but not again.

I'm trying to insert a node at the end of a circular linked list, but after inserting an element for the first time, it gets stuck in the while loop if we try to enter data again.

struct node {
    int data;
    struct node *next;
};

typedef struct node node;
node *head = NULL;

node *insertatend(node *head, int value)
{
    node *temp, *p;
    p = head;
    temp = (node *)malloc(sizeof(node));
    temp->data = value;
    temp->next = head;
    if (head == NULL)
    {
        head = temp;
    }
    else
    {
        while (p->next != head)
            p = p->next;
        p->next = temp;
    }
    return head;
}

void display(node *head)
{
    node *p = head;
    if (head == NULL)
    {
        printf("\nlinked list is empty\n");
        return;
    }
    while (p->next != head)
    {
        printf("%d  ", p->data);
        p = p->next;
    }
    printf("\n");
}

int main()
{
    int ch = 1, value;
    while (ch)
    {
        printf("1.Insert  2.Display");
        scanf("%d", &ch);
        switch (ch)
        {
            case 1:
                printf("enter an element:");
                scanf("%d", &value);
                head = insertatend(head, value);
                break;
            case 2:
                display(head);
                break;
        }
    }
    return 0;
}

Solution

  • I think the mistake is here:

    temp->next=head;
    if(head==NULL){
        head=temp;
    }
    

    When you enter your first element, head is null. So temp->next is set to NULL and head is set to temp. When you enter your second element, it does this:

    else{
    while(p->next!=head)
            p=p->next;
    p->next=temp;}
    

    Where p->next is null, so you will never have the situation that p->next == head and you will always be in the loop!

    Edit: So the solution aproach would be to change it to:

    if(head==NULL){
        head=temp;
    }
    temp->next=head;
    

    Edit: second mistake in the display function: the loop doesn't print the last element. I just tested it and it is working fine.

    So the complete code woud look like:

    #include <stdio.h>
    #include <stdlib.h>
    
    struct node {
        int data;
        struct node *next;
    };
    
    typedef struct node node;
    node *head = NULL;
    
    node *insertatend(node *head, int value)
    {
        node *temp, *p;
        p = head;
        temp = (node *)malloc(sizeof(node));
        temp->data = value;
    
        if (head == NULL)
        {
            head = temp;
        }
        else
        {
            while (p->next != head)
                p = p->next;
            p->next = temp;
        }
        temp->next = head;
        return head;
    }
    
    void display(node *head)
    {
        node *p = head;
        if (head == NULL)
        {
            printf("\nlinked list is empty\n");
            return;
        }
        do
        {
            printf("%d  ", p->data);
            p = p->next;
        } while (p != head);
        printf("\n");
    }
    
    int main()
    {
        int ch = 1, value;
        while (ch)
        {
            printf("1.Insert  2.Display");
            scanf("%d", &ch);
            switch (ch)
            {
                case 1:
                    printf("enter an element:");
                    scanf("%d", &value);
                    head = insertatend(head, value);
                    break;
                case 2:
                    display(head);
                    break;
            }
        }
        return 0;
    }