Linked List Cycle II

2014.1.13 21:43

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:

  This problem doesn't only ask you to check if there is a loop in the list, but also to find out where you enter the loop.

  It is a bit tricky to solve this problem, if you are too accustomed to that "chasing method" that we mentioned in Linked List Cycle.

  Since you only have a "next" pointer, what you can do is to check if $ptr or $ptr->next satisfy some specific property.

  See the following linked list:

  

  Node 2 is the entrance of the loop. Both node 1 and node 4 points to it. If you start traversing the list, you are sure to reach node 2 first and node 4 later. If there is a $ptr pointing to node 4, you reach $ptr->next before you reach $ptr,right? In a normal linked list, this will never happen. That's how we use abnormal condition to detect this abnormal node.

  This problem doesn't use a chasing strategy with two pointers. But it requires one-by-one probing for all nodes until the right one is found, with each probing having O(n) time complexity. Therefore, the overall time complexity is O(n^2), space complexity is O(1).

Accepted code:

 1 // 1CE, 2TLE, 1AC, foolish mistake..
 2 /**
 3  * Definition for singly-linked list.
 4  * struct ListNode {
 5  *     int val;
 6  *     ListNode *next;
 7  *     ListNode(int x) : val(x), next(NULL) {}
 8  * };
 9  */
10 class Solution {
11 public:
12     ListNode *detectCycle(ListNode *head) {
13         // IMPORTANT: Please reset any member data you declared, as
14         // the same Solution instance will be reused for each test case.
15         if(head == nullptr){
16             return nullptr;
17         }
18         
19         ListNode *ptr, *res;
20         
21         res = head;
22         while(res != nullptr){
23             ptr = head;
24             // Forgot to check nullptr, added by the way later.
25             while(ptr != res->next && ptr != nullptr){
26                 if(ptr == res){
27                     // ptr reaches res first, not what we expect
28                     break;
29                 }
30                 // 1TLE here, forgot to move forward...
31                 // 1CE here, ';' is missing!!!!
32                 ptr = ptr->next;
33             }
34             if(ptr == res->next){
35                 // $ptr reaches res->next first, that means $res->next is the start of the loop
36                 // while $res is the end of the loop, thus $ptr = $res->next is the result we want
37                 return ptr;
38             }else{
39                 // 1TLE here, forgot to move forward..
40                 res = res->next;
41             }
42         }
43         
44         return nullptr;
45     }
46 };

 

 posted on 2014-01-13 21:45  zhuli19901106  阅读(148)  评论(0编辑  收藏  举报