10年架構師圖解單鏈表,一篇圖文徹底搞懂


§單鏈表的定義


每一個節點都有一個向后的指針(
引用)指向下一個節點,最后一個節點指向NULL表示結束,有一個Head()指針指向第一個節點表示開始。如下圖:



§單鏈表的特點


耗子戴眼鏡,鼠目寸光
我們只能拿到頭節點,(
在不逐個遍歷的情況下),后面還有多少個節點,它們是什么,它們在哪里,誰是最后一個節點?這些我們統統都無法知道。

肉包子打狗,有去無回
遍歷時只能從前往后,
是單向的,一旦錯過某個節點,只能從頭再遍歷一次,確保這次不要錯過。

§節點的增/刪/交換


增加節點
此時必須有兩個指針,一個指向插入位置
的那個節點,稱它為prev指針,一個指向待插入的節點,稱它為node指針。如下圖:


插入過程相等於鏈接的斷開與重建。如下圖:

用代碼表示:
node.next = prev.next
prev.next = node


刪除節點
此時最好有兩個指針,一個指向待刪除節點前的那個節點,稱它為prev指針,一個指向待刪除節點,稱它為node指針。如下圖:

用代碼表示:
node = prev.next
prev.next = node.next
node.next = NULL


交換節點
此時必須有兩個指針,一個指向待交換的兩個節點前的那個節點,稱它為prev指針,一個指向待交換的兩個節點中的第一個節點,稱它為first指針。如下圖:

用代碼表示:
first = prev.next
prev.next = first.next
first.next = prev.next.next
prev.next.next = first


§逆序


將鏈表的順序倒過來。有兩種方法:依次交換法集體向后轉法

依次交換法
1先和2交換,再和3交換,再和4交換,再和5交換,現在1已經在最后了,2是第一個。如下圖:


2先和3交換,再和4交換,再和5交換,此時2已經是倒數第二個了,3是第一個。如下圖:


依次類推,用3進行一輪交換,再用4進行一輪交換,逆序就完成了。如下圖:

感覺和冒泡排序法有些神似


集體向后轉法
這種方法的思路來自於
體育課一排縱隊和體育老師面對面站着。老師就是頭節點,縱隊就是單鏈表。

縱隊集體向后轉,老師再走過去和新縱隊面對面
單鏈表換了方向,頭節點換了指向

需要三個指針,一個指向
已經向后轉過的部分,稱為done指針;一個指向正要向后轉的那個節點,稱為doing指針;一個指向剩余待向后轉的部分,稱為todo指針。

一開始
還沒有一個向后轉的,因此done = NULL,doing指向第一個,即doing = head,todo指向第二個,即todo = doing.next。如下圖:


讓正在向后轉的節點(即doing)的next指針指向已經向后轉過的(即done);done,doing,todo三個指針分別向右移動一個節點。如下圖是操作過程操作后的結果


用代碼表示:
doing.next = done
done = doing
doing = todo
(如果doing是NULL,結束)
todo = todo.next(如果next是NULL,則賦NULL)


同理,進行一步,如下圖:



同理,最后一步,結束后即完成逆序。如下圖:



兩種方法的比較,一是鏈表的方向不變變換節點位置;二是節點位置不變變換鏈表的方向

§LeetCode,以K個節點為一組逆序

這是leetcode中linkedlist部分的一道題,級別是hard。

如果k=3,每3個節點逆序一下,直到結尾,如果最后剩余的節點不夠3個,則原樣保留。

第一步,0、1、2逆序



第二步,3、4、5逆序



第三步,6、7、8逆序



第四步,9原樣保留



要求:只能定義常量個數的額外變量(或者說只能使用額外常量的內存)。

PS:這道題目雖然是hard級別,但是有了以上的講解,相信大多數人都能做出來。注意邊界條件和細心即可。

相關文章

小學生都能看懂的表達式計算(圖解)

五分鍾輕松了解Hbase列式存儲(圖解)




(完)


編程新說


用獨特的視角說技術

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM