力扣题解:21.合并两个有序链表(C语言)
将两个升序链表合并为一个新的升序链表是一个经典的链表操作问题。可以通过递归或迭代的方法来解决。以下是解释和代码实现:
递归:
每次比较两个链表的头节点,将较小的节点添加到新链表中,并递归处理剩余部分。
-
截至条件:
-
如果 L1 为空,直接返回 L2。
-
如果 L2 为空,直接返回 L1。
-
-
递归步骤:
-
比较 L1 和 L2 的头节点。
-
将较小的节点作为新链表的头节点。
-
递归处理较小节点的下一个节点和另一个链表的头节点。
-
(当某一个链表为空时,返回另一个链表的剩余部分链接到末尾。不需要像迭代法特殊处理)
代码:
struct ListNode* mergeTwoLists(struct ListNode* list1, struct ListNode* list2) {// 如果 list1 为空,直接返回 list2if (list1 == NULL) {return list2;}// 如果 list2 为空,直接返回 list1if (list2 == NULL) {return list1;}// 比较 list1 和 list2 的当前节点值if (list1->val <= list2->val) {// 如果 list1 的当前节点值较小,则将 list1 的当前节点作为合并后链表的当前节点list1->next = mergeTwoLists(list1->next, list2); // 递归合并 list1 的剩余部分和 list2return list1; // 返回 list1 的当前节点作为合并后链表的头节点} else {// 如果 list2 的当前节点值较小,则将 list2 的当前节点作为合并后链表的当前节点list2->next = mergeTwoLists(list1, list2->next); // 递归合并 list1 和 list2 的剩余部分return list2; // 返回 list2 的当前节点作为合并后链表的头节点}
}
迭代:
迭代方法使用一个虚拟头节点(dummy node)作为新链表的头节点,通过一个指针逐步构建新链表。
-
初始化:
-
创建一个虚拟头节点 dummy,其 next 指针指向新链表的头节点。
-
创建一个指针 current,初始指向 dummy。
-
-
迭代步骤:
-
比较 L1 和 L2 的头节点。
-
将较小的节点连接到 current 的 next 指针。
-
移动 current 指针到下一个节点。
-
移动较小节点的链表指针到下一个节点。
-
-
处理剩余部分:
如果 L1 或 L2 中有一个链表已经遍历完,将另一个链表的剩余部分连接到新链表的末尾。
代码:
struct ListNode* mergeTwoLists(struct ListNode* list1, struct ListNode* list2) {struct ListNode dummy;struct ListNode* current = &dummy;
//当两个链表都不为空时,进行迭代while (list1 && list2) {
//将较小的结点链接到新链表中if (list1->val < list2->val) {current->next = list1;list1 = list1->next;} else {current->next = list2;list2 = list2->next;}current = current->next;}
//判断哪个链表为空,将不为空的链表剩余部分连接到新链表的尾端current->next = list1 ? list1 : list2;return dummy.next;
}