/** * Definition for singly-linked list. * struct ListNode { * int val; * ListNode *next; * ListNode(int x) : val(x), next(NULL) {} * }; */ class Solution { public: ListNode *detectCycle(ListNode *head) { if(head==NULL) return NULL; ListNode *fast_node=head; ListNode *slow_node=head; do { if(slow_node->next!=NULL)//慢指针,一次挪一位 slow_node=slow_node->next; else return NULL; if(fast_node->next!=NULL)//快指针,一次挪两位 fast_node=fast_node->next; else return NULL; if(fast_node->next!=NULL)//懒的想花里胡哨的方法了 fast_node=fast_node->next; else return NULL; }while(slow_node!=fast_node);//只要有环一定会有两个指针相遇的情况 int num_cycle=0;//看看环中多少个节点 do { fast_node=fast_node->next; num_cycle++; }while(fast_node!=slow_node); fast_node=head;//让fast_node先走num_cycle-1步 slow_node=head; while(num_cycle!=1)//注意这里是因为指针之差是节点数-1 { fast_node=fast_node->next; num_cycle--; } while(fast_node->next!=slow_node)//二者并行前进,直到fast_node是尾节点,此时slow_node为环起点 { fast_node=fast_node->next; slow_node=slow_node->next; } return slow_node; } };
分析:
这个题也见过,剑指offer,为了检测这个点,要分三步走:
先检测有环不,并检测环中任意节点;
再检测环中个数;
最后让一个指针先走一定步数,然后判断两个指针什么时候处于环的起点终点。