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

2021-09-25 18:41:00 字數 1898 閱讀 5692

如果乙個鍊錶中包含環,如何找到環的入口節點?例如如下圖所示:環的入口節點是節點3;

1.如何在鍊錶中確定有乙個環呢?

2.如何在鍊錶中找到環的入口的節點呢?

基於以上的思考,我們可以想象。

1.使用兩個鍊錶的指標,快指標和慢指標,快指標 (fast)一次移動兩個節點,慢指標 (slow)一次移動乙個節點。當快指標(fast) 的next為空的情況下,說明沒有環。如果 fast == slow 的情況下,說明有環。

2.當fast == slow,說明有環,然後快指標(fast)指向鍊錶的頭結點,慢指標(slow),繼續當前位置,然後 快指標 (fast)一次移動兩個節點,慢指標 (slow)一次移動乙個節點。當 fast 和 slow 再次相遇的時候,此時就是環的入口節點的位置。

對於以上的證明過程如下:

當fast==slow(也就是第一次相遇的時候),fast所經過節點數為2x, slow所經過節點數為x, 假設環中有 n 個節點,fast比slow多走一圈有 2x=n+x; 那麼可以得出 n=x; 可以看出slow實際走了乙個環的步數,

再讓fast指向鍊錶頭部,slow位置不變。

假設鍊錶開頭到環介面的距離是y,那麼x-y表示slow指標走過的除鍊錶開頭y在環中走過的距離,那麼slow再走y步,此時fast結點與slow結點相遇,fast == slow ,x-y+y=x = n,即此時slow指向環的入口。

以上的情況是 當 fast和slow 在第一圈就相遇的情況。但是如果fast 和 slow 在環中迴圈了多圈之後才第一次相遇的話,又該如何。

對於以上的猜測,我們可以證明如下。

當fast==slow(也就是第一次相遇的時候),fast所經過節點數為2x, slow所經過節點數為x, 假設環中有 n 個節點,fast 比 slow多走m圈,有 2x=mn + x; 那麼可以得出 mn=x; 可以看出slow實際走了m個環的步數,

再讓fast指向鍊錶頭部,slow位置不變。

假設鍊錶開頭到環介面的距離是y,那麼x-y表示slow指標走過的除鍊錶開頭y在環中走過的距離,那麼slow再走y步,此時fast結點與slow結點相遇,fast == slow ,x-y+y=x = mn,即此時slow指向環的入口。

package com.offer.test;

import com.lintcode.node.listnode;

/**

* 鍊錶中環的入口節點

* 思路:

* 1.判斷是否有環(如果鍊錶中有cur.next == null ,說明沒有環)

* 2.環的長度(鍊錶中的)

* 3.環的入口節點

* @author [email protected]

* @date 2023年6月19日 上午10:28:10

*/public class meetnodedemo

listnode fast = head.next.next;

listnode slow = head.next;

while (fast != slow) else

} fast = head;

while (fast != slow)

return slow; }

public static void main(string args)

}

劍指offer 鍊錶中環的入口

問題描述 給乙個鍊錶,若其中包含環,請找出該鍊錶的環的入口結點,否則,輸出null。假設x為環前面的路程 紅色路程 a為環入口到相遇點的路程 綠色路程,假設順時針走 c為環的長度 藍色路程 設定快慢指標fast和slow,快指標的速度是慢指標的兩倍 當快慢指標相遇的時候 此時慢指標走的路程為sslo...

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

1.如果鍊錶中有環,可以通過快慢指標,最後快慢指標肯定會相會於環中的某個節點 2.從這個相會的節點開始,當再次遇到該節點,即可統計環中有節點數 n 3.設定兩個指標p,p1,p從頭先走 n 步,p1在頭部,然後兩個指標同時 走,當兩指標相遇時,相遇的節點即是環的入口。c struct listnod...

劍指Offer 鍊錶中環的入口結點

第一步 先找到環中的乙個點 第二步 確定環中有幾個元素,比如n個 第三步 讓第乙個指標先走n步,第二個指標再從頭走,兩指標相遇即為入口結點 class solution def entrynodeofloop self,phead write code here meetingnode self.m...