前言
将用两种解法解这道题:哈希表、双指针
- 第一想法就是用用哈希表,哈希表存其中一个链表的所有节点,看另一个链表中的节点是否存在于哈希表内,存在则相交,反之不相交
- 在看了leetcode题解,还可以用双指针来解这道题。空间复杂度更好,直接变成了常数阶O(1)。大致做法就是让两个指针从不同方向遍历两个链表的每个节点。
一、题目描述
给你两个单链表的头节点 headA
和 headB
,请你找出并返回两个单链表相交的起始节点。如果两个链表不存在相交节点,返回 null
。
具体的题目描述请看leetcode地址
二、解题
2.1 哈希表解法
2.1.1 思路
- 把其中一个链表的所有节点都存入哈希表内
- 访问另一个链表的所有节点,看哈希表内是否存在另一个链表的节点
2.1.2 代码
const getIntersectionNode = function(headA, headB) {
// 任意一个链表为空,不可能相交
if(headA === null || headB === null) return null
// 哈希表
const set = new Set()
// 临时变量,遍历节点用
let temp = headA
// 遍历headA所在链表的所有节点,存入哈希表内
while(temp !== null) {
set.add(temp)
temp = temp.next
}
// 遍历headB所在链表
temp = headB
while(temp !== null) {
// 如果有相同节点说明相交
if(set.has(temp)) return temp
temp = temp.next
}
return temp
}
2.2 双指针解法
2.2.1 思路
- 创建两个指针p、q
- 这两个指针遍历两个链表的每个节点
- 两个指针遍历出发点不一样:分别从不同的链表出发
- 遍历时相遇则说明相交
- 两个指针遍历结束还未相遇,则说明不相交。此时两个指针都指向null,故返回其中一个即可
2.2.2 代码
const getIntersectionNode = function(headA, headB) {
// 任意一个链表为空,不可能相交
if(headA === null || headB === null) return null
// 创建双指针p、q,分别从不同链表头节点开始,遍历两个链表的所有节点
let p = headA
let q = headB
// p、q不相等未遍历继续的条件,
while(p !== q) {
// 指针p依次遍历了以headA为起点的链表 、 以headB为起点的链表
p = p === null ? headB : p.next
// 指针q依次遍历了以headB为起点的链表、 以headA为起点的链表
q = q === null ? headA : q.next
}
// 相交时p为某个节点,不相交时p为null
return p
};