142. 环形链表
自己写的:
/**
* 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) {
ListNode *cur = head;
unordered_set<ListNode *>visited;
while (cur)
{
if (visited.count(cur->next))
{
return cur->next;
}
visited.insert(cur);
cur = cur->next;
}
return cur;
}
};
注意这条语句:visited.insert(cur);
,不要写成 visited.insert(cur->next);
,应该是把当前节点插入哈希集合,而不是把当前节点的下一个节点插入哈希集合,因为在看是否有环时,是根据当前节点的下一个节点是否在当前节点的前面节点中来判断的。
不过,这个解法不是 O(1) 空间。
看了卡哥思路,很巧妙,结合数学分析来解题,有点像小学奥赛。
卡哥视频完美的讲述了这个思路,所有小细节都讲到了。
卡哥代码:
/**
* 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) {
ListNode* fast = head;
ListNode* slow = head;
while(fast != NULL && fast->next != NULL) {
slow = slow->next;
fast = fast->next->next;
// 快慢指针相遇,此时从head 和 相遇点,同时查找直至相遇
if (slow == fast) {
ListNode* index1 = fast;
ListNode* index2 = head;
while (index1 != index2) {
index1 = index1->next;
index2 = index2->next;
}
return index2; // 返回环的入口
}
}
return NULL;
}
};