如果一个链表含有环的话,我们怎么去找到这个环的入口呢?
思路:首先我们知道链表不像数组,有下标可以访问其中的元素。所以我们只能用别的方法来思考,这时我们可以想到利用快慢指针的方法。定义两个指针来同时遍历链表,快指针一次走两个节点,慢指针一次走一个节点。如果快指针=慢指针,我们就知道这个链表确实有环,而且相交的节点是在环内的。我们利用画图与数学知识不难得到快慢指针之间走过的路程关系。
经过简单数学计算可以得到:
实现代码:
/**
* 判断链表是否有环,如果有,返回入环节点的值,没有环,返回null
* @return
*/
public T getLinkCircleVal(){
Entry slow = this.head.next;
Entry fast = this.head.next;
// 使用快慢指针解决该问题
while(fast != null && fast.next != null){
slow = slow.next;
fast = fast.next.next;
if(slow == fast){
break;
}
}
if(fast == null){
return null;
} else {
// fast从第一个节点开始走,slow从快慢指针相交的地方开始走,它们相遇的时候,就是环的入口节点
fast = this.head.next;
while(fast != slow){
fast = fast.next;
slow = slow.next;
}
return slow.data;
}
}