题目描述
给一个链表,若其中包含环,请找出该链表的环的入口结点,否则,输出null。
题解一:利用一个额外的空间,hashmap来保存链表的节点。
import java.util.*;
public class Solution {
public ListNode EntryNodeOfLoop(ListNode pHead)
{
if(pHead==null)
return null;
TreeMap<Integer, ListNode> hash = new TreeMap<>();
while(pHead!=null){
if(hash.containsKey(pHead.val)){
break;
}
hash.put(pHead.val,pHead);
pHead=pHead.next;
}
return pHead;
}
}
题解二:利用快慢指针
如果一个链表没有环,那么遍历链表一定会遇到链表的终点;如果链表有环,那么遍历链表就永远在链表中转下去了。
找到第一个入环节点,具体步骤:
1)设置一个快慢指针,开始的时,快满指针都直线链表的头部,慢指针移动一步,快指针移动两步;
2)如果链表无环,那么快指针一定先到达终点,一旦快指针的next为null 说明没有环存在
3)如果快慢指针相遇了,就说明一定有环,然后快指针重新回到头节点,跨步从之前的两步变为一步,慢指针继续移动一步
4)快慢指针一定会相遇,相遇的节点就是入环节点
public class Solution {
public ListNode EntryNodeOfLoop(ListNode pHead)
{
if(pHead==null||pHead.next==null||pHead.next.next==null)
return null;
//这里慢指针是从头节点的next节点开始的,快指针是头节点的next next节点开始的
ListNode slow=pHead.next,fast=pHead.next.next;
while(slow!=fast){
if(fast.next==null||fast.next.next==null) return null;
slow=slow.next;
fast=fast.next.next;
}
fast=pHead;
while(slow!=fast){
slow=slow.next;
fast=fast.next;
}
return slow;
}
}