問題描述如下:
給定乙個有環的鍊錶,求開始進入環的那個結點,即下圖的 target 。
分析:這個問題可以使用快慢指標來巧妙解決,快指標 fast 每次移動兩個結點,
慢指標 slow 每次移動乙個結點。
當 slow 和 fast 相遇的時候,slow —> target = head —> target = k
即慢指標和頭結點到 target 的距離相同。
這個時候 head 和 slow 一起往後移動,當它們相遇的時候,正好在 target。
現在的問題是「當 slow 和 fast 相遇的時候,slow —> target = head —> target = k」這個結論是如何得到的。
設 fast 和 slow 相遇的時間為 t,slow 的速度為 1,fast 的速度為 2,
當 slow 和 fast 相遇的時候,fast 多走了乙個環,設環的長度為 l 。
即 2 * t - 1 * t = l => t = l
故 slow 走的路程 s = vt = 1*t = t = l
已知 head 到 target 的距離為 k,則 slow 逆向到達 target 的距離為 l-k
而環的長度為 l,因此 slow 正向到達 target 的距離為 l - (l - k) =k
因此 slow —> target = head —> target = k 得證。
// 記錄部落格!求有環鏈表起點 快慢指標相遇時 他們與環起點的距離=head與環起點的距離
#include
using namespace std;
struct node
node
(int n)};
// 很巧妙 快慢指標相遇的時候距離起點是k head距離起點也是k
intgetresult
(node *head)
while
(fast != slow)
; node *p = head->next;
while
(p != slow)
return p->data;
}int
main()
} p->next = pre;
int ans =
getresult
(head)
; cout << ans << endl;
}return0;
}
【end】感謝** 求出有環鏈表的起點(快慢指標)
1.問題描述 給定乙個有環的鍊錶,實現乙個演算法返回環路的開頭節點 有環鏈表的定義 在鍊錶中某個節點的next元素指向在它前面出現過的節點,則表明該鍊錶存在環路 要求 不能夠使用額外的空間來進行記錄 2.題目與之前不一樣的是不能夠開闢額外的空間來進行記錄,所以我們是不能夠使用hashset來判斷哪個...
判斷單鏈表是否有環(快慢指標)
方法一 使用p q兩個指標,p總是向前走,但q每次都從頭開始走,對於每個節點,看p走的步數是否和q一樣。如圖,當p從6走到3時,用了6步,此時若q從head出發,則只需兩步就到3,因而步數不等,出現矛盾,存在環。方法二 使用p q兩個指標,p每次向前走一步,q每次向前走兩步,若在某個時候p q,則存...
快樂數 快慢指標(判斷成環思路)
編寫乙個演算法來判斷乙個數 n 是不是快樂數。快樂數 定義為 對於乙個正整數,每一次將該數替換為它每個位置上的數字的平方和,然後重複這個過程直到這個數變為 1,也可能是無限迴圈但始終變不到 1。如果可以變為1,那麼這個數就是快樂數。如果n是快樂數就返回true 不是,則返回false。示例 輸入 1...