Sort a linked list of 0s, 1s and 2s by changing links

Given a linked list of 0s, 1s and 2s, sort it.

Examples:

Input  : 2->1->2->1->1->2->0->1->0
Output : 0->0->1->1->1->1->2->2->2

Input : 2->1->0
Output : 0->1->2

We have discussed a solution in below post that works by changing data of nodes.
Sort a linked list of 0s, 1s and 2s

The above solution does not work when these values have associated data with them. For example, these three represent three colors and different types of objects associated with the colors and we want to sort objects (connected with a linked list) based on colors.

In this post, a new solution is discussed that works by changing links.

Iterate through the linked list. Maintain 3 pointers named zero, one and two to point to current ending nodes of linked lists containing 0, 1, and 2 respectively. For every traversed node, we attach it to the end of its corresponding list. Finally we link all three lists. To avoid many null checks, we use three dummy pointers zeroD, oneD and twoD that work as dummy headers of three lists.

// CPP Program to sort a linked list 0s, 1s
// or 2s by changing links
#include <stdio.h>

/* Link list node */
struct Node {
    int data;
    struct Node* next;
};

Node* newNode(int data);

// Sort a linked list of 0s, 1s and 2s
// by changing pointers.
Node* sortList(Node* head)
{
    if (!head || !(head->next))
        return head;

    // Create three dummy nodes to point to
    // beginning of three linked lists. These
    // dummy nodes are created to avoid many
    // null checks.
    Node* zeroD = newNode(0);
    Node* oneD = newNode(0);
    Node* twoD = newNode(0);

    // Initialize current pointers for three
    // lists and whole list.
    Node* zero = zeroD, *one = oneD, *two = twoD;

    // Traverse list
    Node* curr = head;
    while (curr) {
        if (curr->data == 0) {
            zero->next = curr;
            zero = zero->next;
            curr = curr->next;
        } else if (curr->data == 1) {
            one->next = curr;
            one = one->next;
            curr = curr->next;
        } else {
            two->next = curr;
            two = two->next;
            curr = curr->next;
        }
    }

    // Attach three lists
    zero->next = (oneD->next) ? (oneD->next) : (twoD->next);
    one->next = twoD->next;
    two->next = NULL;

    // Updated head
    head = zeroD->next;

    // Delete dummy nodes
    delete zeroD;
    delete oneD;
    delete twoD;

    return head;
}

// function to create and return a node
Node* newNode(int data)
{
    // allocating space
    Node* newNode = new Node;

    // inserting the required data
    newNode->data = data;
    newNode->next = NULL;
}

/* Function to print linked list */
void printList(struct Node* node)
{
    while (node != NULL) {
        printf("%d  ", node->data);
        node = node->next;
    }
    printf("\n");
}

/* Drier program to test above function*/
int main(void)
{
    // Creating the list 1->2->4->5
    Node* head = newNode(1);
    head->next = newNode(2);
    head->next->next = newNode(0);
    head->next->next->next = newNode(1);

    printf("Linked List Before Sorting\n");
    printList(head);

    head = sortList(head);

    printf("Linked List After Sorting\n");
    printList(head);

    return 0;
}

Output :

Linked List Before Sorting
1  2  0  1  
Linked List After Sorting
0  1  1  2  

Thanks to Musarrat_123 for suggesting above solution in a comment here.

Time Complexity: O(n) where n is number of nodes in linked list.
Auxiliary Space: O(1)

This article is contributed by Bhaskar Kumar Mishra. If you like GeeksforGeeks and would like to contribute, you can also write an article using contribute.geeksforgeeks.org or mail your article to contribute@geeksforgeeks.org. See your article appearing on the GeeksforGeeks main page and help other Geeks.

Please write comments if you find anything incorrect, or you want to share more information about the topic discussed above.

GATE CS Corner    Company Wise Coding Practice

Recommended Posts:







Writing code in comment? Please use ide.geeksforgeeks.org, generate link and share the link here.