环形链表 II
给定一个链表,返回链表开始入环的第一个节点。 如果链表无环,则返回 null。
先说明一下思路,和网上解法一样。两个指针,一个快指针q(q = q->next->next),一个慢指针p(p->next);
- 假设链表的直线部分长 X,环形部分长 Y,慢指针走的距离为 S,则快指针走的距离为 2S。
- 当两个指针第一次相遇时,存在等式:2S - S = nY(n >= 1, n∈N*),即,S = nY;
此时,令q = head,回到起点,q = q->next; 让快慢指针同时出发,当两者相遇时,便是环的入口;
慢指针距离环入口: Y-(S - X)
及证明:Y-(S - X) + kY = X , 且S = nY 成立即可,
kY = (n-1)Y;
即存在正整数k = (n-1) 使得等式成立。
struct ListNode *detectCycle(struct ListNode *head) {
if(head==NULL || head->next == NULL){
return NULL;
}
struct ListNode *p, *q;
p = head;
q = head;
while(q->next != NULL && q->next->next != NULL){
p = p->next;
q = q->next->next;
if (p == q ){
q = head;
while(1){
//需要考虑到,相遇点就是起点的情况,如:[1,2];
if(p == q){
return q;
break;
}
q = q->next;
p = p->next;
}
}
}
return NULL;
}