求链表是否有环和第一个交点

这道题做起来简单,但是证明比较麻烦。自己的证明很可能有错误,还望指正。

一 是否有环

(1)用追击法,一个指针每次前进1步,另一个指针每次前进2步。

设链表中不包括环的长度为L1,环的长度为L2.

假设走s步之后相交,等价于   式(1)(s-L1)mod L2 = (2s-L1)mod L2有解。即s步之后相交<=>)(s-L1)mod L2 = (2s-L1)mod L2有解

由式(1)得到,n* L2+p=s-L1 (2)

                           m*L2+p=2s-L1 (3)

由(2)(3)得到 (m-n)L2=s (4)

由于s是可变的,上式显然有解。

算法为:一个指针每次前进1步,另一个指针每次前进2步。每次都对比,如果相同则表明相遇,如果到链尾则退出说明没相遇。

(2)而且,我们可以证明在一圈内即可追上。即算法复杂度为O(n)。

当L2>=L1,令s=(L1+k)=L2,保证式子(4)有解

 

当L1>L2,s=(L1+k)=n1 * L2,我们可以知道K可以小于L2(取K=L2-L1modL2)

 

二 求第一个交点

根据式子(4)=> (m-n-1)L2+L2=s => (m-n-1)L2+ P1+P2=L1+P1 <=> (m-n-1)L2+P2=L1

             (P1为定义第一个相交点到追击相遇点的长度,P2为相遇点到第一个相交点的长度,即P1+P2=L2)

这个式子表明链表中不包括环的长度 等于 相遇点到第一个相交点的长度加上环的长度的整数倍。

则算法为:一个指针从相遇点出发,一个指针从链表头开始,而第一次相遇的点即为第一个相交点。

原文地址:https://www.cnblogs.com/catkins/p/5270703.html