本文主要讲解leetcode中141.环形链表和142.环形链表II 基于 HashMap 和 快慢指针两种解法。
一、题目
二、分析
141.环形链表分析
方法一:哈希表
-
思路
我们可以通过检查结点此前是否被访问过来判断链表是否为环形链表。常用的方法是使用哈希表 -
算法
我们遍历所有结点并在哈希表中存储每个结点的引用(或内存地址)。如果当前结点为空结点 null(即已检测到链表尾部的下一个结点),那么我们已经遍历完整个链表,并且该链表不是环形链表。如果当前结点的引用已经存在于哈希表中,那么返回 true(即该链表为环形链表)。 -
优缺点
使用HashMap是最容易想到和常用的方法。但是需要O(N)的空间复杂度。 -
链接:https://leetcode-cn.com/problems/linked-list-cycle/solution/huan-xing-lian-biao-by-leetcode/
方法二:双指针
-
思路
想象一下,两名运动员以不同的速度在环形赛道上跑步会发生什么?
跑的快的运动员一定会追上跑的慢的运动员 -
算法
通过使用具有 不同速度 的快、慢两个指针遍历链表,空间复杂度可以被降低至 O(1)O(1)。慢指针每次移动一步,而快指针每次移动两步。
如果列表中不存在环,最终快指针将会最先到达尾部,此时我们可以返回 false。
现在考虑一个环形链表,把慢指针和快指针想象成两个在环形赛道上跑步的运动员(分别称之为慢跑者与快跑者)。而快跑者最终一定会追上慢跑者。这是为什么呢?考虑下面这种情况(记作情况 A)- 假如快跑者只落后慢跑者一步,在下一次迭代中,它们就会分别跑了一步或两步并相遇。
142.环形链表II分析
方法一:哈希表
思路同141
方法二:双指针
思路和141大致是相同的。但是需要明确3点:
1.本题要求返回入环的第一个节点。
2.快慢指针一次相遇的点并不是入环的第一个节点。
3.当快慢指针第一次相遇时,重新让快指针指向头节点,然后和慢指针一步一步走,再一次相遇的节点就是入环的第一个节点。
推论过程可以参考 :