Leetcode[21] 合并两个有序链表

题目描述

将两个有序链表合并为一个新的有序链表并返回。新链表是通过拼接给定的两个链表的所有节点组成的。

示例:

输入:1->2->4, 1->3->4
输出:1->1->2->3->4->4

题解思路

  1. 迭代法:归并排序的思想,因为两个链表有序,只做一次排序即可,稍作改进,当其中一个有序表结束时,可以将 next 指向另一个链表的剩余节点,不需要遍历完之后作判断,这样节省了比较时间,时间复杂度 O(n + m)
  2. 递归法:终止条件:当 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;
	}
}
发布了52 篇原创文章 · 获赞 81 · 访问量 1万+

猜你喜欢

转载自blog.csdn.net/xiaoma_2018/article/details/104241645