LeetCode Hot100(18/100)——160. 相交链表

文章目录

    • 一、题目描述
    • 二、示例讲解
      • 示例一
    • 三、思维导图
    • 四、解法一:哈希表法
      • 原理说明
      • 流程图展示
      • 时间与空间复杂度
      • Java 实现
    • 五、解法二:双指针法(推荐)
      • 原理说明
      • 示例演示
      • 时间与空间复杂度
      • Java 实现
    • 六、总结

一、题目描述

给定两个单链表 headA 和 headB,找出并返回这两个链表相交的起始节点。如果两个链表没有交点,则返回 null。

链表可能具有 不同的长度,但如果它们相交,会在某个节点之后共享相同的尾部。


二、示例讲解

示例一

假设有如下两个链表:

复制代码
ListA: 4 → 1
             ↘
              8 → 4 → 5
             ↗
ListB:   5 → 6 → 1

它们在节点值为 8 的位置相交,输出应为该节点。


三、思维导图

使用 Mermaid 思维导图可视化题意与解题思路:
两个链表的相交节点
题目理解
两个单链表可能长度不等
若相交则共享尾部部分
否则返回null
解法思路
方法一:哈希表存储节点
方法二:双指针法
复杂度分析
n+m
空间复杂度 O(1) 或 O(n)
关键目标
找出第一个相交节点


四、解法一:哈希表法

原理说明

  1. 首先遍历链表 A,将所有节点加入哈希表。
  2. 然后遍历链表 B,每访问一个节点,检查是否在哈希表中出现过。
  3. 若出现,则该节点即为相交起点;若遍历完未出现,则返回 null。

流程图展示

是
否
开始
遍历链表A
将每个节点加入哈希表
遍历链表B
节点是否在哈希表中?
返回该节点
继续遍历
遍历结束返回null

时间与空间复杂度

  • 时间复杂度:O(n + m)

    其中 n 和 m 分别为两个链表的长度。

  • 空间复杂度:O(n)

    因为需要使用额外哈希表存储链表 A 的节点。

Java 实现

java 复制代码
public class Solution {
    public ListNode getIntersectionNode(ListNode headA, ListNode headB) {
        Set<ListNode> visited = new HashSet<>();
        ListNode currA = headA;
        while (currA != null) {
            visited.add(currA);
            currA = currA.next;
        }

        ListNode currB = headB;
        while (currB != null) {
            if (visited.contains(currB)) {
                return currB; // 找到相交节点
            }
            currB = currB.next;
        }

        return null; // 无相交点
    }
}

五、解法二:双指针法(推荐)

原理说明

使用两个指针 pA 和 pB,分别从链表 A 和 B 的头开始遍历:

  1. 当一个指针到达链表尾端时,从另一条链表的头重新开始。
  2. 两个指针最终会在相交节点相遇,或同时到达 null(不相交)。

这种方法可以"抵消长度差"的影响,使得两个指针在第二次遍历时对齐。

示例演示

指针pB 指针pA 指针pB 指针pA pA 从 headA 开始,pB 从 headB 开始 遍历A 遍历B A到尾时跳到headB B到尾时跳到headA 最终相遇 → 相交节点

时间与空间复杂度

  • 时间复杂度:O(n + m)

    最多遍历两次链表。

  • 空间复杂度:O(1)

    仅使用两个指针,无额外存储。

Java 实现

java 复制代码
public class Solution {
    public ListNode getIntersectionNode(ListNode headA, ListNode headB) {
        if (headA == null || headB == null) return null;
        ListNode pA = headA;
        ListNode pB = headB;

        while (pA != pB) {
            pA = (pA == null) ? headB : pA.next;
            pB = (pB == null) ? headA : pB.next;
        }

        return pA; // 可能为相交节点或null
    }
}

六、总结

解法 思路 时间复杂度 空间复杂度 优点 缺点
哈希表法 存储链表A节点再遍历B查找 O(n+m) O(n) 简单直观 额外空间消耗
双指针法 两指针交替遍历抵消长度差 O(n+m) O(1) 空间最优、优雅 不易直观理解初见者
相关推荐
信奥卷王1 分钟前
[GESP202609 六级] 分树规划
算法
夏幻灵9 分钟前
LeetCode 21:合并两个有序链表——双指针与哑节点详解
算法·leetcode·链表
徐小黑ACG2 小时前
Golang 基础05 结构体struct
开发语言·算法·golang
Navigator_Z2 小时前
LeetCode //C - 1286. Iterator for Combination
c语言·算法·leetcode
北极有牛3 小时前
cpp学习笔记--常量指针
java·开发语言·算法
GPU实战笔记3 小时前
云端 GPU 训练的账户余额提醒:它能说明什么,不能说明什么?
深度学习·算法·成本管理·gpu云计算·云端训练
浮链序3 小时前
怎么证明"你这个模型是偷我的"——把蒸馏变成取证工具
算法·安全·llm
小O的算法实验室3 小时前
IEEE TMC,面向异构物联网的多目标量子行为拓扑优化算法
算法
圣保罗的大教堂4 小时前
leetcode 301. 删除无效的括号 困难
leetcode