劍指offer23 鍊錶中環的入口節點

2021-09-29 07:21:02 字數 1701 閱讀 3380

給乙個鍊錶,若其中包含環,請找出該鍊錶的環的入口結點,否則,輸出null。

遍歷鍊錶,將訪問的節點進行標記,如果出現訪問到該節點時該節點曾經被訪問過,說明該節點就是環的入口節點

/*

struct listnode

};*/

class

solution

return

null;}

};

另外一種方法參考:牛課討論

假設x為環前面的路程(黑色路程),a為環入口到相遇點的路程(藍色路程,假設順時針走), c為環的長度(藍色+橙色路程)

當快慢指標相遇的時候:

此時慢指標走的路程為sslow = x + m * c + a

快指標走的路程為sfast = x + n * c + a

2 sslow = sfast

2 * ( x + m*c + a ) = (x + n *c + a)

從而可以推導出:

x = (n - 2 * m )*c - a

= (n - 2 *m -1 )*c + c - a

即環前面的路程 = 數個環的長度(為可能為0) + c - a

什麼是c - a?這是相遇點後,環後面部分的路程。(橙色路程)

所以,我們可以讓乙個指標從起點a開始走,讓乙個指標從相遇點b開始繼續往後走,

2個指標速度一樣,那麼,當從原點的指標走到環入口點的時候(此時剛好走了x)

從相遇點開始走的那個指標也一定剛好到達環入口點。

所以2者會相遇,且恰好相遇在環的入口點。

最後,判斷是否有環,且找環的演算法複雜度為:

時間複雜度:o(n)

空間複雜度:o(1)

/*

struct listnode

};*/

class

solution

else

return

null;}

//程式執行到這裡說明鍊錶中有環

fast=phead;

while

(fast!=slow)

return slow;}}

;

劍指offer解法

基本思想:

分析:上述思想有點類似於求鍊錶中的倒數第k個節點

/*

struct listnode

};*/

class

solution

else

return

null;if

(fast-

>next)

fast = fast-

>next;

else

return

null;}

listnode *meet = fast;

//相遇節點

//2.環中有幾個節點

int m =0;

dowhile

(fast != slow)

;//3.尋找相遇節點

slow = phead;

fast = phead;

while

(m--

)while

(slow != fast)

return fast;}}

;

劍指offer23 鍊錶中環的入口節點

給乙個鍊錶,若其中包含環,請找出該鍊錶的環的入口結點,否則,輸出null。兩個指標,p1,p2 p1一次走一步,p2一次走兩步。第一次相遇之後開始計數,第二次再相遇時count的值就是環有多少個節點。兩個指標,p1,p2 p1先走count步,然後兩個再同時走,相遇的點就是入口節點。struct l...

劍指offer23 鍊錶中環的入口節點

判斷單鏈表中有沒有環,如果有找到環的入口節點。三個問題 1 如何確定鍊錶中包含環 兩個指標,乙個指標一次走一步,乙個指標一次走兩步。如果走得快的指標追上了走得慢的指標,則說明鍊錶包含環 如果走得快的指標走到了鍊錶末尾 p next null 都沒有追上第乙個指標,則無環。2 如何找到環的入口 定義兩...

劍指offer 23 鍊錶中環的入口節點

給乙個鍊錶,若其中包含環,請找出該鍊錶的環的入口結點,否則,輸出none。思路 1.找相遇點 設定乙個快指標pfast乙個慢指標pslow,先找到乙個相遇點,一定在環中 2.計算環的長度 從相遇點出發,到相遇點結束 1,即為環的長度。3.pfast 從phead 環的長度出發 pslow從phead...