Leetcode[21] 合并两个有序链表
题目描述
将两个有序链表合并为一个新的有序链表并返回。新链表是通过拼接给定的两个链表的所有节点组成的。
示例:
输入:1->2->4, 1->3->4
输出:1->1->2->3->4->4
题解思路
- 迭代法:归并排序的思想,因为两个链表有序,只做一次排序即可,稍作改进,当其中一个有序表结束时,可以将 next 指向另一个链表的剩余节点,不需要遍历完之后作判断,这样节省了比较时间,时间复杂度 O(n + m)
- 递归法:终止条件:当 l1 或 l2 为空时,返回剩余 l2 或 l1 结束;
返回值为每一层都已排好序的头指针;
递归内容:当 l1 的值 val 较小时,l1 的 next 指向之后排完序的链表头,否则,l2 的 next 指向排好序的链表头;
时间复杂度:O(n + m)空间复杂度也是一样,递归会消耗(n + m)个栈空间
AC代码
迭代算法:
/**
* Definition for singly-linked list.
* struct ListNode {
* int val;
* struct ListNode *next;
* };
*/
struct ListNode* mergeTwoLists(struct ListNode* l1, struct ListNode* l2){
if(!l1 || !l2) {
return l1 == NULL ? l2 : l1;
}
struct ListNode *head = NULL;
if(l1 -> val < l2 -> val) {
head = l1;
l1 = l1 -> next;
}
else {
head = l2;
l2 = l2 -> next;
}
struct ListNode *p = head;
while(l1 || l2) {
if(!l1) {
p -> next = l2; break;
}
else if(!l2) {
p -> next = l1; break;
}
else if(l1 -> val < l2 -> val) {
p -> next = l1;
p = p -> next;
l1 = l1 -> next;
}
else {
p -> next = l2;
p = p -> next;
l2 = l2 -> next;
}
}
return head;
}
递归算法:
struct ListNode* mergeTwoLists(struct ListNode* l1, struct ListNode* l2){
if(l1 == NULL || l2 == NULL) {
return l1 == NULL ? l2 : l1;
}
else if(l1 -> val < l2 -> val) {
l1 -> next = mergeTwoLists(l1 -> next, l2);
return l1;
}
else {
l2 -> next = mergeTwoLists(l1, l2 -> next);
return l2;
}
}
所有博客均在CSDN首发 Caso_卡索 https://blog.csdn.net/xiaoma_2018