给定一个链表,返回链表开始入环的第一个节点。 如果链表无环,则返回 null
。
说明:不允许修改给定的链表。
进阶:
你是否可以不用额外空间解决此题?
原文地址http://www.cnblogs.com/ranranblog/p/5587079.html
如下图所示,X,Y,Z分别为链表起始位置,环开始位置和两指针相遇位置,则根据快指针速度为慢指针速度的两倍,可以得出:
2*(a + b) = a + b + n * (b + c);即
a=(n - 1) * b + n * c = (n - 1)(b + c) +c;
注意到b+c恰好为环的长度,故可以推出,如将此时两指针分别放在
起始位置和
相遇位置,并以相同速度前进,当一个指针走完距离a时,另一个指针恰好走出 绕环n-1圈加上c的距离。
故两指针会在环开始位置相遇。(换位置后第一次相遇)
#include<cstdlib>
class Solution {
public:
ListNode *detectCycle(ListNode *head) {
bool cycle = false;
int counter;
ListNode *start = NULL;
if(head == NULL)
{
return start;
}
ListNode *p1,*p2;
p1 = p2 = head;
while(p2->next != NULL && p2->next->next != NULL)
{
p1 = p1->next;
p2 = p2->next->next;
if(p1 == p2)
{
cycle = true;
p2 = head;
while(p1 != p2)
{
p1 = p1->next;
p2 = p2->next;
}
start = p1;
break;
}
}
return cycle ? start : NULL;
}
};
有了上一篇判断链表有无环之后,现在关键是找 环的入口节点,自己怎么也找不到,嗯,记住吧。