1、描述
給定乙個鍊錶,返回鍊錶開始入環的第乙個節點,如果鍊錶無環,則返回null。
為了表示給定鍊錶中的環,我們使用整數pos 來表示鍊錶尾連線到鍊錶中的位置(索引從0開始)。如果pos 是 -1,則在該鍊錶中沒有環。
說明:不允許修改給定的鍊錶
例1:輸入:head = [3, 2, 0, -4] pos = 1
輸出:true
解釋:鍊錶中有乙個環,其尾部連線到第二個結點
例2:輸入:head = [1, 2] pos = 0
輸出:true
解釋:鍊錶中有乙個環,其尾部連線到第乙個結點
2、演算法
1)雜湊表
思想:我們分配乙個 set 去儲存所有的列表節點。我們逐一遍歷列表,檢查當前節點是否出現過,如果節點已經出現過,那麼一定形成了環且它是環的入口。否則如果有其他點是環的入口,我們應該先訪問到其他節點而不是這個節點。其他情況,沒有成環則直接返回 nil
時間複雜度:o(n)
func detectcycle(_ head:listnode?)->listnode?else
head = head?.next
}return nil
}
2)雙指標
思想:雙指標
演算法被劃分成兩個不同的 階段 :
在第一階段,找出列表中是否有環,如果沒有環,可以直接返回 null 並退出。
否則,用 相遇節點 來找到環的入口。
時間複雜度:o(n)
func detectcycle2(_ head:listnode?)->listnode?
//如果這裡有乙個環,快/慢指標就會有乙個相遇節點,反之,返回nil
let intersect = getintersect(head)
if intersect == nil
//用兩個相同速度的指標,乙個從煉表頭開始,乙個從相遇節點開始,當它們指向同乙個節點時,這個結點就是環的入口
var ptr1 = head
var ptr2 = intersect
while ptr1?.val != ptr2?.val
return ptr1
}private class func getintersect(_ head:listnode?)->listnode?
}return nil
}
演算法 環形鍊錶 II
輸入 head 3,2,0,4 pos 1輸出 tail connects to node index 1解釋 鍊錶中有乙個環,其尾部連線到第二個節點。輸入 head 1,2 pos 0輸出 tail connects to node index 0解釋 鍊錶中有乙個環,其尾部連線到第乙個節點。pu...
環形鍊錶 II
給定乙個鍊錶,返回鍊錶開始入環的第乙個節點。如果鍊錶無環,則返回 null。為了表示給定鍊錶中的環,我們使用整數 pos 來表示鍊錶尾連線到鍊錶中的位置 索引從 0 開始 如果 pos 是 1,則在該鍊錶中沒有環。說明 不允許修改給定的鍊錶。示例 1 輸入 head 3,2,0,4 pos 1 輸出...
環形鍊錶II
1.問題描述 給定乙個鍊錶,返回鍊錶開始入環的第乙個節點。如果鍊錶無環,則返回null。為了表示給定鍊錶中的環,我們使用整數pos來表示鍊錶尾連線到鍊錶中的位置 索引從 0 開始 如果pos是 1,則在該鍊錶中沒有環。說明 不允許修改給定的鍊錶。示例 1 輸入 head 3,2,0,4 pos 1 ...