持续创作,加速成长!这是我参与「掘金日新计划 · 6 月更文挑战」的第12天,点击查看活动详情
一、题目描述:
给定一个链表,如果它是有环链表,实现一个算法返回环路的开头节点。若环不存在,请返回 null。
如果链表中有某个节点,可以通过连续跟踪 next 指针再次到达,则链表中存在环。 为了表示给定链表中的环,我们使用整数 pos 来表示链表尾连接到链表中的位置(索引从 0 开始)。 如果 pos 是 -1,则在该链表中没有环。注意:pos 不作为参数进行传递,仅仅是为了标识链表的实际情况。
示例 1:
输入:head = [3,2,0,-4], pos = 1 输出:tail connects to node index 1 解释:链表中有一个环,其尾部连接到第二个节点。 示例 2:
输入:head = [1,2], pos = 0 输出:tail connects to node index 0 解释:链表中有一个环,其尾部连接到第一个节点。 示例 3:
输入:head = [1], pos = -1 输出:no cycle 解释:链表中没有环。
进阶:
你是否可以不用额外空间解决此题?
来源:力扣(LeetCode) 链接:leetcode.cn/problems/li… 著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。
二、思路分析:
根据题意可知,当链表中有环时,遍历链表是走不到尽头的。如果遍历到空节点,说明链表无环;那么可以使用快慢指针的方式。
用一快一慢两个指针从链表头开始遍历,快指针每次走2步,慢指针每次走1步;
进入环后,快指针每次会追上慢指针1步,所以若链表有环,快指针一定会追上慢指针;
当两个指针相等时,假设慢指针走了k步,那么快指针一定走了2k步,且此时快指针超过了慢指针若干圈,而且是正好超过整数圈,所以它们才会相遇。则快指针比慢指针多走的这k步,是环中节点个数的整数倍;
这时把其中一个指针挪到链表头部继续遍历,两指针每次走一步,当它们再次相遇时,相遇的节点就是链表环入口
三、AC 代码:
public class Solution {
public ListNode detectCycle(ListNode head) {
if (head == null) {
return null;
}
ListNode slow = head, fast = head;
while (fast != null) {
slow = slow.next;
if (fast.next != null) {
fast = fast.next.next;
} else {
return null;
}
if (fast == slow) {
ListNode ptr = head;
while (ptr != slow) {
ptr = ptr.next;
slow = slow.next;
}
return ptr;
}
}
return null;
}
}
四、总结:
掘友们,解题不易,留下个赞或评论再走吧!谢啦~ 💐
希望对你有帮助,期待您找到心意的工作和满意的offer
期待下次再见~
\