最近在刷leetcode
的題,對環形鍊錶方面的題做個總結
**:二、帶環鍊錶入口
環形鍊錶-力扣(leetcode)
解法一:快慢指標
我們定義兩個指標,初始位置都放在頭節點的地方,然後快慢指標一起走,快指標一次走兩步(需要注意邊界條件),慢指標一次走一步,如果快指標走到nullptr
,該鍊錶就不帶環;如果快慢指標相遇,該鍊錶就帶環。
為什麼這個辦法可以解決,我們是需要給出理論依據的,先舉個最常見的例子,兩個人在操場跑步,乙個人的速度是另乙個人的兩倍,如果跑的快的人追上跑的慢的人,那麼快的人必然超過慢的人一圈。那麼在鍊錶中,也是一樣的:
如果使用快慢指標,他們會在4
的位置相遇,此時就可以返回了。
我們給出**:
// 快慢指標
class solution
listnode* fast = head;
listnode* slow = head;
dowhile(slow != fast);
return true;}};
複雜度分析:
空間複雜度o(1)
附上一張通過的圖:
解法二:雜湊表/map
我們遍歷所有結點並在map
中儲存每個結點的引用(或記憶體位址)。如果當前結點為空結點nullptr
(即已檢測到鍊錶尾部的下乙個結點),那麼我們已經遍歷完整個鍊錶,並且該鍊錶不是環形鍊錶。如果當前結點的引用已經存在於map
中,那麼返回true
(即該鍊錶為環形鍊錶)。
// map
class solution
mapkey;
listnode* pcur = head;
while(pcur)
else
pcur = pcur->next;
}return false;}};
複雜度分析:
map
可以解決,unordered_map
當然也可以解決
class solution
unordered_mapkey;
listnode* pcur = head;
while(pcur)
else
pcur = pcur->next;
}return false;}};
至於set
和unordered_set
,自己試試就知道了。
複雜度分析:
附圖:
解法三: 非常規做法
堆位址從低到高,leetcode的鍊錶記憶體是順序申請的,如果有環,附上**:head->next
一定小於head
環形鍊錶ii-力扣(leetcode)
解法一:快慢指標
上一道題目,已經詳細講解了快慢指標判斷鍊錶帶環,其實我們可以利用快慢指標相遇的節點,我們需要發覺一下這個點的魅力。
我們把節點增多幾個,節點太少不好觀察:
我們假設煉表頭結點到環入口位置距離為a,環的入口與相遇節點位置距離為b,環的長度為r,我們計算快慢指標所走過的距離:
d(fast) = a + b + n * r
d(slow) = a + b
快指標的速度是慢指標的兩倍,相同時間,快指標所走過的路程應該是慢指標所走過路程的兩倍,於是:
d(fast) = 2 * d(slow)
所以有:a = n * r - b
當n = 1時,也就是快指標走了一圈之後,在第二圈的時候遇見了慢指標,a = r - b
我們可以發現,a是鍊錶的表頭到環的入口點的位置,(r - b)是相遇點到環入口點的位置。
但是我們需要考慮一種特殊情況,鍊錶是首尾相連的:
我們可以發現,如果鍊錶的表頭就是入口點,使用快慢指標的時候,因為快指標是慢指標的速度的2倍,所以它們一定是慢指標走了一圈,快指標走了兩圈的時候相遇,就是在環的入口點相遇。
附上**:
class solution
listnode *slowptr = head;
listnode *fastptr = head;
/** 快慢指標
* 如果快指標追上慢指標,說明鍊錶帶環
* 並且快慢指標相遇的點一定是換上的一點
*/do
while(slowptr != fastptr);
/** 讓慢指標回到頭節點位置
* 然後快慢指標一起走
* 再次相遇的地方必然是環的入口
* 原因:
*/slowptr = head;
while(slowptr != fastptr)
return slowptr; }};
附上圖:
解法二:非常規做法
堆的位址從低到高,leetcode
的鍊錶記憶體是順序申請的,如果有環,head->next
一定小於head
class solution
head = head->next;
}return nullptr;}};
附圖:
鍊錶專題2 環形鍊錶 II
給定乙個鍊錶,判斷鍊錶中是否有環。為了表示給定鍊錶中的環,我們使用整數 pos 來表示鍊錶尾連線到鍊錶中的位置 索引從 0 開始 如果 pos 是 1,則在該鍊錶中沒有環。示例 1 輸入 head 3,2,0,4 pos 1 輸出 tail connects to node index 1 解釋 鍊...
鍊錶 環形鍊錶
環形鍊錶也叫迴圈鍊錶 可以是雙鏈表 也可以是單鏈表 操作原理和單鏈表差不多,只是最後乙個節點不在指向空 null 而是頭 head 這裡以單鏈表舉例 description 環形鍊錶 author lzq date 2018 11 3 20 46 version 1.0 public class a...
鍊錶 環形鍊錶
題目描述 給定乙個鍊錶,返回鍊錶開始入環的第乙個節點。如果鍊錶無環,則返回 null。為了表示給定鍊錶中的環,我們使用整數 pos 來表示鍊錶尾連線到鍊錶中的位置 索引從 0 開始 如果 pos 是 1,則在該鍊錶中沒有環。注意,pos 僅僅是用於標識環的情況,並不會作為引數傳遞到函式中。說明 不允...