leetcode 141 环形链表
题目内容:
给定一个链表,判断链表中是否有环。
如果链表中有某个节点,可以通过连续跟踪 next 指针再次到达,则链表中存在环。 为了表示给定链表中的环,我们使用整数 pos 来表示链表尾连接到链表中的位置(索引从 0 开始)。 如果 pos 是 -1,则在该链表中没有环。注意:pos 不作为参数进行传递,仅仅是为了标识链表的实际情况。
如果链表中存在环,则返回 true 。 否则,返回 false 。
原题链接:https://leetcode-cn.com/problems/linked-list-cycle
有环的话,遍历一遍节点肯定有重复的,用unordered_map存储下节点即可,如果有重复的则返回false,一直到链表末都没有重复的则返回true。
但这种方法并不是最好的,需要大量的空间(hash table,同时链表大的时候,hash table的rehash也十分的耗时间);这种链表判环问题很经典,一般用快慢指针来解决,相当于追及问题,一个指针跑的快,一个指针跑的慢,快的指针就会先进环,慢的随后进去,由于快指针跑的快,在一定时刻快指针就会追上慢指针,追上了则说明存在环。
快指针走两步,即next->next
慢指针走一步,即next
代码如下:
/**
* Definition for singly-linked list.
* struct ListNode {
* int val;
* ListNode *next;
* ListNode(int x) : val(x), next(NULL) {}
* };
*/
class Solution {
public:
bool hasCycle(ListNode *head) {
if(head == NULL || head->next==NULL) return false;
ListNode *slow = head;
ListNode *fast = head->next;
while(slow != fast){
if(fast == NULL || fast->next == NULL ) return false;
fast = fast->next->next;
slow = slow->next;
}
return true;
}
};