(leetcode)力扣100 27合并两个有序链表(迭代/递归)

题目

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

数据范围

两个链表的节点数目范围是 [0, 50]

-100 <= Node.val <= 100

l1 和 l2 均按 非递减顺序 排列

测试用例

示例1

java 复制代码
输入:l1 = [1,2,4], l2 = [1,3,4]
输出:[1,1,2,3,4,4]

示例2

java 复制代码
输入:l1 = [], l2 = []
输出:[]

示例3

java 复制代码
输入:l1 = [], l2 = [0]
输出:[0]

题解1 (迭代,时间O(N+M),空间O1)

java 复制代码
/**
 * 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 mergeTwoLists(ListNode list1, ListNode list2) {
        ListNode res=new ListNode(-1);
        ListNode pre=res;

        while(list1!=null&&list2!=null){
            if(list1.val<=list2.val){
                pre.next=list1;
                list1=list1.next;
            }else{
                pre.next=list2;
                list2=list2.next;
            }
            pre=pre.next;
        }


        pre.next=list1 == null? list2:list1;

        return res.next;
    }
}

题解2(递归,时空O(N+M))

java 复制代码
/**
 * 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 mergeTwoLists(ListNode list1, ListNode list2) {
        if(list1==null){
            return list2;
        }else if(list2==null){
            return list1;
        }else if(list1.val<=list2.val){
            list1.next=mergeTwoLists(list1.next,list2);
            return list1;
        }else{
            list2.next=mergeTwoLists(list1,list2.next);
            return list2;
        }
    }
}

思路

这道题没有特殊要求的话,舅姥姥老老实实用迭代吧,思路清晰,空间复杂度也低,不需要额外说明什么,就是设计了一个指针来记录头,另一个指针来遍历两个list。

递归的话代码较少,但思路麻烦,空间复杂度也高,但最好也掌握一下,万一被问到了呢?他的思路如下:

java 复制代码
我们可以把这个过程想象成**"层层外包"**的任务。

1. 核心思想:大任务化小任务
我们要合并两个链表,其实只需要做一件事:

比较两个链表的头节点,选出较小的那个作为合并后的头,然后把剩下的部分交给别人去处理。

2. 生活中的例子:排队领书
假设有两队学生(l1 和 l2),每个队都按身高从小到大排列。现在我们要把他们合并成一队。

比较: 你站在门口,看两队排头的人。发现 l1 的排头兵 A 比 l2 的排头兵 B 矮。

决定: 你让 A 站到新队伍的第一位。

外包(递归): 你对 A 说:"剩下的事情我不管了,你去连接后面的人吧。"

递归调用: A 于是回头看了一眼剩下的学生(l1 扣除 A 后的部分,以及完整的 l2 队),重复你刚才的操作。

3. 代码逻辑拆解
让我们对照你提供的 Java 代码来看:

出口(边界情况):

if (l1 == null) return l2; // 如果 l1 没学生了,剩下的全是 l2 的,直接接上去
if (l2 == null) return l1; // 反之亦然
这是递归的"底",没有它程序就会无限循环。

选择与连接:

if (l1.val < l2.val) {
    // l1 赢了,l1 成为当前的头
    // 关键:l1.next 等于【剩下的 l1】和【完整的 l2】合并的结果
    l1.next = mergeTwoLists(l1.next, l2); 
    return l1; // 返回已经接好的自己
}
相关推荐
weisian15111 小时前
Java并发编程--47-分布式ID生成器:雪花算法(Snowflake)与时钟回拨问题
java·算法·时钟回拨·雪花算法id
itzixiao11 小时前
L1-066 猫是液体(5分)[java][python]
java·开发语言·python·算法
ytttr87311 小时前
MATLAB SIFT图像配准实现
算法·机器学习·matlab
小饕11 小时前
从 Word2Vec 到多模态:词嵌入技术的演进全景
人工智能·算法·机器学习
海参崴-11 小时前
AVL树完整实现与深度解析
算法
一个爱编程的人11 小时前
一个数是不是素数
数据结构·算法
Hui_AI72012 小时前
基于RAG的农产品GEO溯源智能问答系统实现
开发语言·网络·人工智能·python·算法·创业创新
lwf00616412 小时前
FFM (Field-aware Factorization Machine) 学习日记
算法·机器学习
南宫萧幕12 小时前
HEV能量管理控制算法实战:从MPC/RL理论基础到Simulink闭环建模
算法·matlab·汽车·控制·pid
IT猿手12 小时前
SCI一区:章鱼优化算法(Octopus Optimization Algorithm, OOA)求解23个测试函数,出图丰富,提供完整MATLAB代码
开发语言·算法·matlab