We use cookies to ensure you have the best browsing experience on our website. Please read our cookie policy for more information about how we use cookies.
yea .... i start comparing elements of both linked lists A and B(say) one by one from beginning and my final solution will be the linked list A .
so here's how it works :- if the element of A is less than B then i simply move the pointer by one position in forward direction and if the element in list B is less then i need to incorporate that element in A and for that i use temp pointer and this time i move pointer of b forward by one since i have parsed it's element. And finally when i have parsed all elements of one list then i know i no longer need to compare and simply join the other remaining list to my solution (the first three ifs take care of this case).
Thanks for sharing your solution Dark _ Knight19! I had figured out the "base case," but I was struggling with finishing the recursive part. I rewrote your code based on etayluz' comment and also slightly more efficient (it's less understandable than your code but less checks based on prior logic).
I think that the nested 'else if' wont be a much help in this case as the condition needs to be checked for all three 'if's in a case where A & B are not null. In case one of them is null it gets terminated without checking the remaining 'if's as it just simply returns a value. so I found no great optimization with nested 'else if' with this solution. Correct me if I am wrong. Happy coding.
It very simple. The mergeLists function is called many times. Each time the input in sys.stdin more than last time. So we have to find out where we are and where we're going. That is q and p. Once we know that, we can get only the new stuff.
The new stuff we store in a. But there are traps! The very first data is nonsense, so we pop it off. Then the next data is also a trap, but it is a number that tells us where the next trap is. Those traps are all in the same way, so we pop them all off in a while loop.
All we have left is pure data. But the data has to be in the right order to make the checkmarks green. So we sort the data. First we sort by the length of the data, because the longer the data is, the more valuable it is. Then we sort by the content of data, which sometimes makes it more valuable too, but not as much as the length.
When the data is nice and ordered, we can put it all together and write it up on the fptr. That is how the data escapes the program and makes you winner.
Hi D_K, I just wonder if your code will compare the remaining of class A in case B is all null already, but A is still unsorted ?
because I see you only compare A and B, and when B is null, such as when A has 10 elements and B has only 1 element, program just stop after pushing that one element of B into minimal position in A without going further and sort A.
Can someone explain to me how the previous node in A points to the new value of A after it has passed. Let me explain:
A: 1->3->NULL
....^
B: 2->4->6->NULL
....^
Initially we start at the head of the lists.
Since 1 < 2 it becomes
A: 1->3->NULL
..........^
B: 2->4->6->NULL
....^
Now, I understand that 2 points to 3 and 4 becomes the new head after that block of code, but when does 1 point to 2 since the pointer has already passed it? To me, it looks like 1 and 2 are pointing to 3.
Very nice! Here is C solution using while loop.
Not as elegant but easier to understand:
Node* MergeLists(Node *headA, Node* headB)
{
if (headA == NULL && headB == NULL) {
return NULL;
}
if (headA == NULL) {
return headB;
}
if (headB == NULL) {
return headA;
}
// Ensure that list A starts with the smaller number
if (headA->data > headB->data) {
Node *tmp = headB;
headB = headA;
headA = tmp;
}
Node *listHead = headA;
while (headB) {
// Advance through nodes in list A until the next node
// has data bigger than data at current node of list B
while (headA->next != NULL &&
headB->data > headA->next->data) {
headA = headA->next;
}
// Insert current node in list B into list A
Node* nextB = headB->next;
headB->next = headA->next;
headA->next = headB;
headB = nextB;
}
return listHead;
}
No, you need this. The first one handles if they are both NULL. The second handles if only one is NULL. If we ask about if one is NULL, without knowing about the second, we would need yet another if statement inside of it.
Thank you for this,it is realy helpful,and apart from that if you can give me some resources to understand recursion cause I am not getting it in an effective manner.
thanks.
If you move the return statement to inside your conditional blocks, you can clean up your headA > headB code by just allowing it to return headB. Here's my solution in Java:
Node MergeLists(Node a, Node b) {
if (a == null) {
return b;
} else if (b == null) {
return a;
}
if (a.data < b.data) {
a.next = MergeLists(a.next, b);
return a;
} else {
b.next = MergeLists(a, b.next);
return b;
}
}
You can also test for one node == null at a time as I did; if either is null it returns the other, and if both are null returning the second node still returns null which is equivalent to what if((headA==NULL)&&(headB==NULL)) does.
this part of code essentially means, the next element to head 1(element 4) would be the result of the comparison between 4 and next head2's element which is 2.
now the result of the comparison between 4 and 2 would be assigned next to 4.
so, if head1's element is the largest, that ll be the final result of final comparison in this part of the code. but it would fail in the case, where 4(head1) is compared to 10(head2), where it goes to the else part.
here head1's next element,i.e 5 is compared to current head2 i.e 10, again first part of code(comparison if clause) is executed, where it again fails coz 10>5. then 10 is compared to 6, and again 10>6. so head1 is returned, which is 6,with the head2 s elemnt i.e 10. and if you observe closely , this comparison was assigned to head1(6)'s next.
now this 10 will bubble up to the previous part where it becomes 6->10. now this link moves up and becomes 5->6->10, which moves up to be 4->5->6->10, again 2->4->5->6->10 and finally becomes 1->2->4->5->6->10.
these 4 lines took me a while to understand
Node* tmp= headB;
headB = headB->next;
temp->next = headA; the original headB now points to headA
headA = temp; headA now becomes original headB
It can be written as:
Node* tmp = headA;
headA = headB; // change the headA to headB
headA->next = MergeLists(tmp, headB->next); //tmp is the orginal headA
I hope people can usnstand it better with these 3 lines.
Node*MergeLists(Node*headA,Node*headB){// This is a "method-only" submission. // You only need to complete this method if(headA==NULL&&headB!=NULL)returnheadB;if(headB==NULL&&headA!=NULL)returnheadA;if(headA==NULL&&headB==NULL)returnNULL;if(headA->data<headB->data){headA->next=MergeLists(headA->next,headB);returnheadA;}headB->next=MergeLists(headA,headB->next);returnheadB;}
Brilliant code!! Can u pls explain why u added headA=temp?? I think the work is completed with temp as soon as u assign temp->next=headA;
And can u pls tell me why u r u returning headA for the whole code at the end?? it'd be great if u helped :)
My almost similar code in Java. Did not use Recursion because it will give overflow issue with bigger lists.
NodeMergeLists(NodeheadA,NodeheadB){Nodemerged=newNode();NodemergedTemp=merged;// taking a copy of the head node of new array.while(headA!=null||headB!=null){// while any of the list has nodes leftif(headA!=null&&headB!=null){//while both have elemntsif(headA.data<=headB.data)// if list 1 has smaller element add its node to the new list.{merged.next=headA;headA=headA.next;}else{// else add list 2's elementmerged.next=headB;headB=headB.next;}}elseif(headA==null){// if list 1 is out of nodes we only add list 2's elementsmerged.next=headB;headB=headB.next;}elseif(headB==null){// else if list 2 is out of elements we add list 1's elements;merged.next=headA;headA=headA.next;}merged=merged.next;}returnmergedTemp.next;// I started storing elemnts from next location actually thus passing merged.next as head.}
Essentially the same thing but little clean and easy to understand
/* class Node { int data; Node next; }*/NodemergeLists(NodeheadA,NodeheadB){Nodea=headA;Nodeb=headB;Nodec=null;if(a==null||b==null)// either of them is nullreturna==null?b:a;// getting the first index pointed by c, done this so now in the coming loop i can use next directly on cif(a.data<b.data){c=a;a=a.next;}else{c=b;b=b.next;}Nodehead=c;// either one of a or b has been changed,while(a!=null&&b!=null){// ie going to the last elements of the linked listsif(a.data<b.data){c.next=a;a=a.next;}else{c.next=b;b=b.next;}c=c.next;}// either one of a and b is finished// a is leftif(a!=null)c.next=a;// b is leftif(b!=null)c.next=b;returnhead;}
much simplified. same concept but it is easier to just chain with the first parameter and recursively place the smallest head list in that first parameter
We can simplify your solution even furthur. The following is almost the same but appeared easier to understand to me. Actually the else block is simplified.
You are hitting python's default recursion limit (which is quite conservative). Either revert your implementation into loops or use sys.setrecursionlimit() to increase the recursion depth.
Thank you Dark_Knight19 for posting your solution! I was struggling with solving this non-recusively for hours, and your post inspired me to try a recursive solution.
we are not allocating any memory to temp. therefore if headB value changes to headB.next then temp value has to change to same value as temp and headB are pointing to same address. Can you explain why it is not changing.
This is so much better than the code given in editorial.
This solution does not need extra space to store the Node. (Although it does have a temp Node pointer, but node pointer is fine, storing the object Node would be big space consuming and interviewer will definitely ask to improve upon the solution given in the editorial)
Btw, you can also avoid to have that extra temp node pointer in the else condition.
Merge two sorted linked lists
You are viewing a single comment's thread. Return to all comments →
Here is a simple recursive solution that passes both test cases!
}
Can u explain ur code?
yea .... i start comparing elements of both linked lists A and B(say) one by one from beginning and my final solution will be the linked list A . so here's how it works :- if the element of A is less than B then i simply move the pointer by one position in forward direction and if the element in list B is less then i need to incorporate that element in A and for that i use temp pointer and this time i move pointer of b forward by one since i have parsed it's element. And finally when i have parsed all elements of one list then i know i no longer need to compare and simply join the other remaining list to my solution (the first three ifs take care of this case).
I think you're not addressing the case where:
headA->data == headB->data
I would make this change in the forth if statement:
if(headA->data <= headB->data)
Umm yeah i think i forgot that .... thanks for pointing it out :)
Thanks for sharing your solution Dark _ Knight19! I had figured out the "base case," but I was struggling with finishing the recursive part. I rewrote your code based on etayluz' comment and also slightly more efficient (it's less understandable than your code but less checks based on prior logic).
I think that the nested 'else if' wont be a much help in this case as the condition needs to be checked for all three 'if's in a case where A & B are not null. In case one of them is null it gets terminated without checking the remaining 'if's as it just simply returns a value. so I found no great optimization with nested 'else if' with this solution. Correct me if I am wrong. Happy coding.
You are right. We can just have:
here is problem solution in python java c++ and c programming. https://solution.programmingoneonone.com/2020/07/hackerrank-merge-two-sorted-linked-lists-solution.html
for those who need it in java, here it is!
Nice one. I did it this way Node mergeLists(Node headA, Node headB) { if (headA == null && headB == null) return null; else if (headA == null) return headB; else if (headB == null) return headA; if(headA.data <= headB.data){ headA.next = mergeLists(headA.next, headB); return headA; } else { headA.next = mergeLists(headA, headB.next); return headB; } }
did it work?
here is problem solution in python java c++ and c programming. https://solution.programmingoneonone.com/2020/07/hackerrank-merge-two-sorted-linked-lists-solution.html
Thanks
nice solution.
The latter part of the code can be slightly shortened:
Code post mat kar hero. bakiyo ko bhi karne de thodi mehnat.
@pvamsii43 what is the difference if you write the last else condition as given below?
I tried this code and it gave a non terminating output.
SinglyLinkedListNode* mergeLists(SinglyLinkedListNode* head1, SinglyLinkedListNode* head2) { if(head1==NULL && head2==NULL){ return NULL; } if(head1==NULL && head2!=NULL){ return head2; } if(head1!=NULL && head2==NULL){ return head1; } if(head1->data<=head2->data){ head1->next=mergeLists(head1->next,head2); } else{ head2->next=mergeLists(head1,head2->next);
} if(head1->data<=head2->data){ return head1; } else{ return head2; }
}
sugoi
SinglyLinkedListNode* mergeLists(SinglyLinkedListNode* head1, SinglyLinkedListNode* head2) {
} well..I think my code is easier to understand
where is mergeLists function
it is the main function thats we are calling again and again matlab recrusive
i don't think there is a need to check if both head1 and head2 are NULL.. question states that "either" may be NULL
please send de solution
if (headA == NULL && headB == NULL) return NULL; else if (headA == NULL) return headB; else if (headB == NULL) return headA;
if(headA->data <= headB->data) headA->next = MergeLists(headA->next, headB);
else { Node* temp = headB; headB = headB->next; temp->next = headA; headA = temp; headA->next = MergeLists(headA->next, headB); }
return headA;
Can you please explain the else part
No problem! I give you best solution. In python the third.
please explain your code
It very simple. The mergeLists function is called many times. Each time the input in sys.stdin more than last time. So we have to find out where we are and where we're going. That is q and p. Once we know that, we can get only the new stuff.
The new stuff we store in a. But there are traps! The very first data is nonsense, so we pop it off. Then the next data is also a trap, but it is a number that tells us where the next trap is. Those traps are all in the same way, so we pop them all off in a while loop.
All we have left is pure data. But the data has to be in the right order to make the checkmarks green. So we sort the data. First we sort by the length of the data, because the longer the data is, the more valuable it is. Then we sort by the content of data, which sometimes makes it more valuable too, but not as much as the length.
When the data is nice and ordered, we can put it all together and write it up on the fptr. That is how the data escapes the program and makes you winner.
here is problem solution https://code.programmingoneonone.com/2020/09/get-node-value-solution-hackerrank.html
Then ..this is simpler version:-
As always Recursive approach is great.
yeah...you just need to understand recursion to be able to use it with ease.
Hi D_K, I just wonder if your code will compare the remaining of class A in case B is all null already, but A is still unsorted ? because I see you only compare A and B, and when B is null, such as when A has 10 elements and B has only 1 element, program just stop after pushing that one element of B into minimal position in A without going further and sort A.
It is correct in case A is already sorted tho.
The question says A and B are already sorted.
Can someone explain to me how the previous node in A points to the new value of A after it has passed. Let me explain:
A: 1->3->NULL
....^
B: 2->4->6->NULL
....^
Initially we start at the head of the lists. Since 1 < 2 it becomes
A: 1->3->NULL
..........^
B: 2->4->6->NULL
....^
Now, I understand that 2 points to 3 and 4 becomes the new head after that block of code, but when does 1 point to 2 since the pointer has already passed it? To me, it looks like 1 and 2 are pointing to 3.
SinglyLinkedListNode* mergeLists(SinglyLinkedListNode* p, SinglyLinkedListNode* q) { SinglyLinkedListNode* sm, *startm; if(p->data<=q->data) { startm=p; p=p->next; } else { startm=q; q=q->next; } sm=startm; while(p!=NULL&&q!=NULL) { if(p->data<=q->data) { sm->next=p; sm=sm->next; p=p->next; } else { sm->next=q; sm=sm->next; q=q->next; } } if(p==NULL) sm->next=q; else sm->next=p; return startm; }
cant we do this firrst add all the elements and than sort it???
Did you get the answer of your question?
here is problem solution in java python c++ c and javascript programming. https://programs.programmingoneonone.com/2021/05/hackerrank-merge-two-sorted-linked-lists-solution.html
Very nice! Here is C solution using while loop. Not as elegant but easier to understand:
First check (headA == NULL && headB == NULL) is not necessary because the following two will handle it.
No, you need this. The first one handles if they are both NULL. The second handles if only one is NULL. If we ask about if one is NULL, without knowing about the second, we would need yet another if statement inside of it.
I disagree. If both are NULL, then
will trigger and return NULL since that is what headB equals to. And we did expect NULL, so the case of two NULLs is indeed redundant.
it will handle it because if both are null when you check the first list it runs true and return second which is null itself so null is returned
I believe you can set nextB = headA->next at once and skip the extra step of changing the pointer with headB->next.
Thank you for this,it is realy helpful,and apart from that if you can give me some resources to understand recursion cause I am not getting it in an effective manner. thanks.
while (headA->next != NULL && headB->data > headA->next->data)
while(head1->next->data < head2->data && head1->next != NULL)
if i change 1 while loop condition to 2 while loop condition then it is showing runtime error why both condition are not same?
If you move the return statement to inside your conditional blocks, you can clean up your headA > headB code by just allowing it to return headB. Here's my solution in Java:
You can also test for one node == null at a time as I did; if either is null it returns the other, and if both are null returning the second node still returns null which is equivalent to what if((headA==NULL)&&(headB==NULL)) does.
Nicely done!!
Do you think this is a bit simpler? I know it tests twice.
PS: How to attach code?
You need to press enter twice followed by a tab:
And then enter for a new line in the code. The text appears brown when it's formatted as code.
If you want syntax highlighting, you can use the following syntax:
Replace "java" with the language of your choice. python3, ruby, c++, etc.
didn't work
Recursive approach are the best. How did you come up with a recursive approach. I am always solving questions with iterative approaches.
Can you please explain your code?
consider head1: 4 ->5 ->6 and head2: 1 ->2 ->10 i am sure you might have understood if head1 is null then return head2, and vice versa now with.
if(head1.data>=head2.data) { head2.next=mergeList(head1,head2.next); return head2; }
so, if head1's element is the largest, that ll be the final result of final comparison in this part of the code. but it would fail in the case, where 4(head1) is compared to 10(head2), where it goes to the else part.
here head1's next element,i.e 5 is compared to current head2 i.e 10, again first part of code(comparison if clause) is executed, where it again fails coz 10>5. then 10 is compared to 6, and again 10>6. so head1 is returned, which is 6,with the head2 s elemnt i.e 10. and if you observe closely , this comparison was assigned to head1(6)'s next.
now this 10 will bubble up to the previous part where it becomes 6->10. now this link moves up and becomes 5->6->10, which moves up to be 4->5->6->10, again 2->4->5->6->10 and finally becomes 1->2->4->5->6->10.
hope it helped understand recursion.
Sweet..nice solution!
wow so simple to understand
amazing
This is pretty!
What's the time complexity of your solution?
I like this solution. What is the time complexity over in this solution.
I converted this to Python but Tests 5 and 6 are failing is it beacuse of recursion stack full?
This is a beautiful solution
Nice solution. For the first three checks, you can simplify to:
Because if they are both null, this will just return null which is what we want. But if only one is null, it will return the other.
these 4 lines took me a while to understand Node* tmp= headB; headB = headB->next; temp->next = headA; the original headB now points to headA headA = temp; headA now becomes original headB
It can be written as: Node* tmp = headA; headA = headB; // change the headA to headB headA->next = MergeLists(tmp, headB->next); //tmp is the orginal headA
I hope people can usnstand it better with these 3 lines.
The various solutions in this thread can be further simplified to
My code, which passes all tests:
Tip: recursion can be by itself confusing, so writing less code, keeps confusion out of the way ;)
Hey @whoiscris can u pls explain how does the code work?? I'm stuck by the recursion part here :( i don't get it right
Can you please explain your code by taking an example?? I am new to recursion.
why not change the recursive part to this (java code):
awesome.. thank you so much
Simpler:
Simpler
how else if part of code work ,plss explain.
I get inspiration from your answer:
Brilliant code!! Can u pls explain why u added headA=temp?? I think the work is completed with temp as soon as u assign temp->next=headA; And can u pls tell me why u r u returning headA for the whole code at the end?? it'd be great if u helped :)
My almost similar code in Java. Did not use Recursion because it will give overflow issue with bigger lists.
Essentially the same thing but little clean and easy to understand
Thanks for this nice and easy to understand solution.
why you wrote it as merged.next instead of merged simply.
why you wrote it as merged.next
Why this is not working , can anybody give me the explaination please
headA->next = MergeLists(headA->next, headB); can you explain the meaning of this line/
much simplified. same concept but it is easier to just chain with the first parameter and recursively place the smallest head list in that first parameter
Superb!
Node mergeLists(Node headA, Node headB) { if(headA == null) return headB; else if(headB == null) return headA; Node head = new Node(); if(headA.data < headB.data){ head = headA; head.next = mergeLists(headA.next,headB); }else{ head = headB; head.next = mergeLists(headA,headB.next); } return head; }
Thank you @Dark_Knight19 for giving the solution here only, god bless you bro.
Nice code..!!
We can simplify your solution even furthur. The following is almost the same but appeared easier to understand to me. Actually the else block is simplified.
if((headA==null)&&(headB==null)) return null; if((headA!=null)&&(headB==null)) return headA; if((headA == null)&&(headB!=null)) return headB;
instead of else if in last section it should be only else.
JAva 7
if (head1 == null && head2 == null) { return null; } if (head1 == null) { return head2; } if (head2 == null) { return head1; } if (head2.data <= head1.data) { SinglyLinkedListNode temp = head2; head2 = head2.next; temp.next = head1; head1 = temp; head1.next = mergeLists(head1.next, head2); } else { head1.next = mergeLists(head1.next, head2); } return head1;
Hi Mikelee89
Would you mind to explain, why return head1 can have result sequence of number from low to high?
Test Case 5 and 6 showing runtime error in python
You are hitting python's default recursion limit (which is quite conservative). Either revert your implementation into loops or use
sys.setrecursionlimit()
to increase the recursion depth.U did have to add an greater than equal sign to the else if statement to run the code
else if((headA->data) >= (headB->data))
Thank you Dark_Knight19 for posting your solution! I was struggling with solving this non-recusively for hours, and your post inspired me to try a recursive solution.
I ended up coming up with this solution:
C++ simple
Hi,
In Node* temp = headB,
we are not allocating any memory to temp. therefore if headB value changes to headB.next then temp value has to change to same value as temp and headB are pointing to same address. Can you explain why it is not changing.
this is simpler
SinglyLinkedListNode* mergeLists(SinglyLinkedListNode* head1, SinglyLinkedListNode* head2) { if(head1==NULL && head2==NULL) { return head1; } else if(head1==NULL) { return head2; } else if(head2==NULL) { return head1; } else { if (head1->datadata) { head1->next=mergeLists( head1->next,head2 ); return head1;
} else { head2->next=mergeLists(head1,head2->next); return head2; }
} }**
much shorter version:
python3
greate jugaad !!! smart work !!!
If we can use array then what is the point of solving LL problems?
Haha, I was also tempted to convert it to a list, but then told my self the exact same thing.
why headA = temp ? i don't understand this part
It exceeds the recursion depth
Would these two work in place of the first 3 if-statement above?
if ((headA==NULL) return headB; if ((headB==NULL) return headA;
The idea is that even if both are NULL, it will just return the other which is NULL.
Am I missing something in my though ?
nice
On similar lines
This is so much better than the code given in editorial.
This solution does not need extra space to store the Node. (Although it does have a temp Node pointer, but node pointer is fine, storing the object Node would be big space consuming and interviewer will definitely ask to improve upon the solution given in the editorial)
Btw, you can also avoid to have that extra temp node pointer in the else condition.
An iterative solution in Python
Interesting. Is that in C or is it pseudocode?
here is simple code in java...
instead of writing three condition for checking null like this:
if((headA==NULL)&&(headB==NULL) return NULL; if((headA!=NULL)&&(headB==NULL)) return headA; if((headA == NULL)&&(headB!=NULL)) return headB;
you can write:
if(head1==nullptr) return head2;
if(head2==nullptr) return head1;
Here is another solution with recursive {
}
super