环形链表 II

前言:

这道题是前面环形链表那道题的一个拓展,如果朋友们感兴趣的话可以去看一下:

https://blog.csdn.net/2302_76561054/article/details/135179129

题目描述:

给定一个链表的头节点 head ,返回链表开始入环的第一个节点。 如果链表无环,则返回 null。

如果链表中有某个节点,可以通过连续跟踪 next 指针再次到达,则链表中存在环。 为了表示给定链表中的环,评测系统内部使用整数 pos 来表示链表尾连接到链表中的位置(索引从 0 开始)。如果 pos 是 -1,则在该链表中没有环。注意:pos 不作为参数进行传递,仅仅是为了标识链表的实际情况。

不允许修改 链表。

示例:

在这里插入图片描述
题目链接https://leetcode.cn/problems/linked-list-cycle-ii/description/

解题思路及图示:

我们在前面的环形链表的题目中已经找到了环中快慢指针(快指针一次走两步,慢指针一次走一步)的相遇点,所以在此题中通过数学推导可以知道,让一个指针从起始点开始走,一个指针从环中相遇点开始走,当两指针相遇处就是入环点。

数学推导:

在这里插入图片描述

注意在慢指针入环后,慢指针一定在遍历完环的第一圈前被追上,可以这样想快慢指针每走一次二者间距离就缩短一个节点,当慢指针走完一圈时,那么二者间距离就缩短环的节点数?所以,慢指针一定在遍历完环的第一圈前被追上。

解法图示:

在这里插入图片描述

示例代码:

typedef struct ListNode LN;
struct ListNode *detectCycle(struct ListNode *head) {
    //由数学推导可得,当一个指针从起始点开始走,另一指针从相遇点(上一题中)开始走时,当两指针走到相遇时,此节点就是进环处
    LN* slow=head;
    LN* fast=head;

    while(fast&&fast->next)
    {
        slow=slow->next;
        fast=fast->next->next;

        if(slow==fast)//找到快慢指针相遇处
        {
            LN* meet=fast;
            LN* cur=head;
            while(cur!=meet)//一个指针从起始点开始走,另一指针从相遇点开始走时
            {
                cur=cur->next;
                meet=meet->next;
            }
            return meet;//两指针相遇,此节点就是进环处
        }
    }

    return NULL;
}
  • 9
    点赞
  • 11
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值