Given a linked list, return the node where the cycle begins. If there is no cycle, return null.
Follow up:
Can you solve it without using extra space?
Solution:
/**
* Definition for singly-linked list.
* class ListNode {
* int val;
* ListNode next;
* ListNode(int x) {
* val = x;
* next = null;
* }
* }
*/
public class Solution {
public ListNode detectCycle(ListNode head) {
if(head==null) return null;
ListNode ptr1=head, ptr2=head;
while(ptr1!=null && ptr2!=null){
if(ptr1.next==null || ptr2.next==null || ptr2.next.next==null) return null;
ptr1=ptr1.next;
ptr2=ptr2.next.next;
if(ptr1==ptr2)
break;
}
ptr1=head;
while(ptr1!=ptr2){
ptr1=ptr1.next;
ptr2=ptr2.next;
}
return ptr1;
}
}设圈前长度为x, 两指针在圈中相遇位置为k,圈周长为r。设相遇时ptr1跑了m圈,ptr2跑了n圈。因为ptr2速度是ptr1两倍,有:
2(x+k+mr) = x+k+nr
x+k = (n-m)r
因n和m均为整数且n>m,x+k应为整数圈。因为ptr1和ptr2在圈内位置为k,再跑x会到达圈起始点。从head跑x,同样会到达圈的起始点。所以讲ptr1移动到head,和ptr2以步长为1一起移动,相遇处就是圈的起始点。

本文介绍了一种在不使用额外空间的情况下检测并找到循环链表起始节点的方法,详细解释了算法原理和实现过程。
737

被折叠的 条评论
为什么被折叠?



