LeetCode题解--141.环形链表

1. 题目

给定一个链表,判断链表中是否有环。
进阶:
你能否不使用额外空间解决此题?

2. 测试

  1. 输入:[1] no cycle,输出false;
  2. 输入:[1,2] no cycle,输出false;
  3. 输入:[3,0,-2,4] tail connects to node index 1, 输出true.

3. 分析

我们首先画一下如果链表存在环的情况,如下图所示。
这里写图片描述
  如果链表存在环,那么这个链表一定从某一个节点开始会出现环的入口,最后,遍历经过一圈之后还会回到入口处。题目要求检查是否存在环,那么最直接的方法是检查遍历链表的过程中是否出现某一个节点被遍历了两次。
  以上面的图为例,从节点3进入后经过4,5,6,7,8后仍然会回到节点3,那么这个时候就节点3被遍历了两次,那么就很容易想到第一种哈希表法

3.1 哈希表法

  使用一个指针遍历链表,每次访问一个节点首先都判断Hashset中是否存在同一个节点,如果存在则链表存在环,否则持续加入到Hashset中。当指针遍历到NULL的时候仍然没有找到环,证明链表不存在环。
  上面的哈希表法很容易构思,但是不满足进阶要求中的空间复杂度是O(1)的条件,那么则构思出第二种方法双指针法

3.2 双指针法

  双指针在链表的操作中比较常见,应该作为一种常用的思路记住。还以上面的图为例,我们设置两个指针从head开始遍历,规定两个指针的前进速度不一样,分别称为快、慢指针,如下图所示,slow指针每次前进一个,fast指针每次前进两个节点。
这里写图片描述
  因为fast指针每次前进两个,一定比slow指针先到达环的入口处。而当slow指针进入环的时候,fast指针已经经过了两个节点,如下图所示。这个时候,我们将这个过程想象成400m跑步的追及问题。如果存在环的话,因为fast指针速度更快,一定会追上slow指针。而如果fast指针没有追上slow指针,一定是因为链表不存在环。
这里写图片描述

4. C++程序(双指针法)

  1. 特殊情况1:空链表不成环;
  2. 特殊情况2:单节点不自成环。
bool hasCycle(ListNode *head) {
        if(head==NULL||head->next==NULL) return false;       //空链表无环,单个节点也无环        
        ListNode *fast=head,*slow=head;
        while(fast!=NULL&&fast->next!=NULL){            
            slow = slow->next;
            fast = fast->next->next;            
            if(fast == slow) return true;
        }
        return false;                
    }

5. 提交结果

这里写图片描述

  • 3
    点赞
  • 5
    收藏
  • 打赏
    打赏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
©️2022 CSDN 皮肤主题:编程工作室 设计师:CSDN官方博客 返回首页
评论 1

打赏作者

GuanghaoChen

你的鼓励将是我创作的最大动力

¥2 ¥4 ¥6 ¥10 ¥20
输入1-500的整数
余额支付 (余额:-- )
扫码支付
扫码支付:¥2
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、C币套餐、付费专栏及课程。

余额充值