05. Sort a Linked List of 0s, 1s and 2s
β GFG solution to Sort a Linked List of 0s, 1s and 2s problem: segregate nodes containing 0s, 1s, and 2s using optimal pointer manipulation technique. π
The problem can be found at the following link: π Question Link
π§© Problem Description
Given the head of a linked list where nodes can contain values 0s, 1s, and 2s only. Your task is to rearrange the list so that all 0s appear at the beginning, followed by all 1s, and all 2s are placed at the end.
A linked list is a linear data structure where elements are stored in nodes, and each node contains data and a reference to the next node. The goal is to segregate the nodes based on their data values while maintaining the relative order within each group.
π Examples
Example 1
Input: head = 1 β 2 β 2 β 1 β 2 β 0 β 2 β 2
Output: 0 β 1 β 1 β 2 β 2 β 2 β 2 β 2
Explanation: All the 0s are segregated to the left end of the linked list, 2s to the right end of the list, and 1s in between.
Example 2
Input: head = 2 β 2 β 0 β 1
Output: 0 β 1 β 2 β 2
Explanation: After arranging all the 0s, 1s and 2s in the given format, the output will be sorted.
π Constraints
$1 \le \text{no. of nodes} \le 10^6$
$0 \le \text{node->data} \le 2$
β
My Approach
The optimal approach uses Three-Way Partitioning with Pointer Manipulation to efficiently segregate nodes without using extra space for new nodes:
Node Segregation with Tail Pointers
Initialize Pointers:
Create separate head and tail pointers for each category:
zero
,one
,two
(heads) andzeroTail
,oneTail
,twoTail
(tails).All pointers initially set to
nullptr
.
Traverse and Segregate:
Iterate through the original list, breaking the
next
links to isolate each node.Based on node data (0, 1, or 2), append the node to the respective category list.
Update both head and tail pointers for efficient O(1) appending.
Link Categories:
Connect the three segregated lists:
zeros β ones β twos
.Handle edge cases where any category might be empty.
Determine the final head based on which categories exist.
Return Result:
Return the head of the newly constructed segregated list.
π Time and Auxiliary Space Complexity
Expected Time Complexity: O(n), where n is the number of nodes in the linked list. We traverse each node exactly once to segregate them into three categories.
Expected Auxiliary Space Complexity: O(1), as we only use a constant amount of additional space for pointer variables, regardless of the input size. No extra nodes are created.
π§βπ» Code (C++)
class Solution {
public:
Node* segregate(Node* head) {
if (!head) return head;
Node* zero = nullptr, *one = nullptr, *two = nullptr;
Node* zeroTail = nullptr, *oneTail = nullptr, *twoTail = nullptr;
while (head) {
Node* next = head->next;
head->next = nullptr;
if (head->data == 0) {
if (!zero) zero = zeroTail = head;
else zeroTail = zeroTail->next = head;
} else if (head->data == 1) {
if (!one) one = oneTail = head;
else oneTail = oneTail->next = head;
} else {
if (!two) two = twoTail = head;
else twoTail = twoTail->next = head;
}
head = next;
}
if (zeroTail) {
head = zero;
zeroTail->next = one ? one : two;
if (oneTail) oneTail->next = two;
} else if (oneTail) {
head = one;
oneTail->next = two;
} else {
head = two;
}
return head;
}
};
β Code (Java)
class Solution {
public Node segregate(Node head) {
if (head == null) return head;
Node zero = null, one = null, two = null;
Node zTail = null, oTail = null, tTail = null;
while (head != null) {
Node next = head.next;
head.next = null;
if (head.data == 0) {
if (zero == null) zero = zTail = head;
else zTail = zTail.next = head;
} else if (head.data == 1) {
if (one == null) one = oTail = head;
else oTail = oTail.next = head;
} else {
if (two == null) two = tTail = head;
else tTail = tTail.next = head;
}
head = next;
}
if (zTail != null) {
head = zero;
zTail.next = (one != null) ? one : two;
if (oTail != null) oTail.next = two;
} else if (oTail != null) {
head = one;
oTail.next = two;
} else {
head = two;
}
return head;
}
}
π Code (Python)
class Solution:
def segregate(self, head):
if not head:
return head
zero = one = two = None
z_tail = o_tail = t_tail = None
while head:
next_node = head.next
head.next = None
if head.data == 0:
if not zero:
zero = z_tail = head
else:
z_tail.next = head
z_tail = head
elif head.data == 1:
if not one:
one = o_tail = head
else:
o_tail.next = head
o_tail = head
else:
if not two:
two = t_tail = head
else:
t_tail.next = head
t_tail = head
head = next_node
if z_tail:
head = zero
z_tail.next = one if one else two
if o_tail:
o_tail.next = two
elif o_tail:
head = one
o_tail.next = two
else:
head = two
return head
π§ Contribution and Support
For discussions, questions, or doubts related to this solution, feel free to connect on LinkedIn: π¬ Any Questions?. Let's make this learning journey more collaborative!
β If you find this helpful, please give this repository a star! β
πVisitor Count
Last updated