線性數據結構
動態數組、棧和隊列,底層都是依託靜態數組
,靠resize解決固定容量的問題。(而動態數組之所以叫做動態,是因爲它從用戶的角度來看的,實現它的底層依靠的是靜態數組。)
鏈表與上面的三種線性數據結構都不同,它是真正的動態數據結構
。
鏈表的重要性
- 最簡單的動態數據結構
- 深入理解引用(C/C++中的指針),引用與內存相關
- 更深入理解遞歸,鏈表本身具有清晰的遞歸結構
- 具有功能性,組織圖結構,哈希表。
鏈表 Linked List
- 把數據存儲在一種單獨的結構中,通常叫做“節點”(Node)。
- 對於鏈表的節點,通常只有兩部分內容
class Node{
E e; // 一部分存儲真正的數據
Node next; //另一部分,next指向當前節點的下一個節點
}
對於鏈表,可以比作一輛火車,每一個節點是一節車廂,在車廂中存儲真正的數據,車廂與車廂之間需要進行連接使數據是整合在一起的。用戶可以方便的在這些數據上進行查詢等操作,數據與數據之間的連接是由next完成
的。
假如第一節車廂存儲元素1,同時它還有一個連接下一節車廂的車鏈(即指向下一個節點的next,是一個Node類型的引用);下一節車廂存儲了元素2,它還有一個next指向下一節車廂;假如下一個節點存儲了元素三,繼續指向下一個節點,這個過程不是無窮無盡的,鏈表存儲的數據一定是有限的。假如火車只有三節車廂,那麼第三節車廂後什麼也沒有,也就是第三個節點的next存儲的是NULL。如此以來,如果一個節點的next是空了,則說明這個節點一定是最後一個節點,這就是鏈表的原理。
如果我還需要存儲數據,給火車後面加車廂就可以了。所以鏈表的優點在於它是真正的動態數據結構,不需要像靜態數組一樣處理固定容量的問題
。
對於鏈表,需要存儲多少個數據,就生成多少個節點把它們掛接起來,但同時,鏈表也喪失了隨機訪問的能力
,不能像數組一樣用索引取值。這是因爲從底層機制上數組開闢的空間在內存裏是連續分佈的,可以直接用O(1)的操作拿出數據;鏈表由於是靠next一層一層連接,在計算機的底層每一個節點它所在的內存的位置是不同的,必須依靠next來找到元素,這也是鏈表最大的缺點。
數組與鏈表簡單對比
- 數組最好用於索引有語意的情況,鏈表則不適合有語意。
- 數組最大優點支持快速查詢,而鏈表最大優點是動態。
鏈表節點的簡單結構
將節點設計成一個私有的內部類,對用戶屏蔽
LinkedList.java
// 支持泛型
public class LinkedList<E> {
// 節點設計成鏈表類中的內部類
// 設計私有類,只有在鏈表數據結構內纔可以訪問到Node
private class Node {
// 設計成public 在LinkedList中可以隨意訪問操作 不需要設置get,set方法
public E e; // 存放元素
public Node next; // 指向Node的引用
public Node(E e, Node next) {
// 將用戶傳來的數據交給節點
this.e = e;
this.next = next;
}
// 用戶只傳來e
public Node(E e) {
this(e, null);
}
// 用戶什麼都不傳
public Node() {
this(null, null);
}
// 對每一個節點設置toString方法
@Override
public String toString() {
// 每一個節點,直接打印e所對應的toString
return e.toString();
}
}
}
寫在最後
如果代碼有還沒有看懂的或者我寫錯的地方,歡迎評論,我們一起學習討論,共同進步。
推薦學習地址:
liuyubobobo老師的《玩轉數據結構》:https://coding.imooc.com/class/207.html
最後,祝自己早日鹹魚翻身,拿到心儀的Offer,衝呀!