判斷鏈表是否有環及環入口點的求法


首先,判斷一個單鏈表是否有環。網上有很多解法就是設置兩個指針fast,slow分別指向鏈表頭部,然后同時向后遍歷。fast步長為2即每次走兩步,slow每次走一步。如果fast走到鏈表尾部則肯定沒有環,因為如果有環肯定是如下圖所示的樣子。

如果fast和slow相遇則有環。有沒有可能在有環的情況下fast和slow永遠不相遇呢?假設在某個時間slow走過的路程為S而且slow已經在環上了,則fast走過的為2S。因為fast是速度是slow的兩倍。假設環的長度為L,fast和slow不相遇的條件就是(2S - S) % L != 0永遠成立,因為fast和slow相遇即在某一時刻fast比slow多走過了n(n>=1)圈,(2S - S) % L == S % L != 0是不是會永遠成立?明顯不會,因為S每次增加1,總有一天會等於0成立。

現在假設已經知道了有環,來求環的入口點。

如上圖所示,我們先作如下的假設:

鏈表起點為A點;

環的入口為B點;

fast和slow的相遇點為C;

鏈表的方向為順時針;

A到B的距離為X;

B到C的距離為Z;

C到B的距離為Y。

則有如下的結果成立:

1. X + Z = S;

2. X + Z + nL = 2S;

3. Y + Z = L;

即X + Z + nL = 2X + 2Z -> X = nL - Z = nL - (L - Y) = (n - 1)L + Y。最后的結果就是X = (n - 1)L + Y,其中n>=1。也就是說從A和C點同時出發,以步長為1遍歷鏈表,那么在C處出發的指針在多走了n-1圈之后與從A出發的指針在B處相遇。也就是說兩個指針指向同一個節點的時候這個點就是環的入口點。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM