I am trying to sort a Linked List using mergesort in Java. However, I am not getting the sorted Linked List as output. This is the code:-
/**
* Definition for singly-linked list.
* public class ListNode {
* int val;
* ListNode next;
* ListNode() {}
* ListNode(int val) { this.val = val; }
* ListNode(int val, ListNode next) { this.val = val; this.next = next; }
* }
*/
class Solution {
public ListNode sortList(ListNode head) {
if(head==null||head.next==null){
return head;
}
ListNode middle = findMiddle(head);
ListNode rightHead = middle.next;
middle.next = null;
ListNode leftHead = head;
leftHead = sortList(leftHead);
rightHead = sortList(rightHead);
return merge(leftHead,rightHead);
}
public ListNode merge(ListNode leftHead, ListNode rightHead){
ListNode dummyHead = new ListNode(-1);
ListNode temp = dummyHead;
while(leftHead!=null && rightHead!=null){
if(leftHead.val<rightHead.val){
temp.next = leftHead;
temp = leftHead;
leftHead = leftHead.next;
}else{
temp.next = rightHead;
temp = rightHead;
rightHead = rightHead.next;
}
// temp = temp.next;
}
if(leftHead!=null){
temp.next = new ListNode(leftHead.val);
leftHead = leftHead.next;
temp = temp.next;
}
else if(rightHead!=null){
temp.next = new ListNode(rightHead.val);
rightHead = rightHead.next;
temp = temp.next;
}
return dummyHead.next;
}
public ListNode findMiddle(ListNode head){
ListNode slow = head;
ListNode fast = head.next;
while(fast!=null && fast.next!=null){
slow = slow.next;
fast = fast.next.next;
}
return slow;
}
}
I have used the standard mergeSort algorithm which is used to sort Arrays just the data type is changed to Linked List. There are no compiler errors so I guess something has to be wrong with my logic.
Your issue is in the merge
function. After the first while
loop, you are using a if-else
case which just merging only 1 node, but it should be merged through while loop to merge the whole remaining part.
For example :
left = [2, 3]
right = [1]
according to your code :
after end of while loop : mergedList = [1]
then if(leftHead!=null)
satisfy. After that if condition : mergedList = [1, 3]
but there is still a node remaining in left part.
while(leftHead!=null){
temp.next = new ListNode(leftHead.val);
leftHead = leftHead.next;
temp = temp.next;
}
while(rightHead!=null){
temp.next = new ListNode(rightHead.val);
rightHead = rightHead.next;
temp = temp.next;
}
But, you can use if-else too as it's a LinkedList. You can do as following, when you are just adding the remaining part in the end, that might save your code a little running time too.
if(leftHead!=null){
temp.next = leftHead;
}
else if(rightHead!=null){
temp.next = rightHead;
}