從0開始學算法5:線性表

一、什麼是線性表

線性表的定義是描述其邏輯結構,而通常會在線性表上進行的查找、插入、刪除等操作。

線性表作爲一種基本的數據結構類型,在計算機存儲器中的映象(或表示)一般有兩種形式,一種是順序映象,一種是鏈式映象。

二、線性表的順序存儲

1.定義

若將線性表L=(a0,a1, ……,an-1)中的各元素依次存儲於計算機一片連續的存儲空間,這種機制表示爲線性表的順序存儲結構。

2.特點

  • 邏輯上相鄰的元素 ai, ai+1,其存儲位置也是相鄰的;
  • 存儲密度高,方便對數據的遍歷查找。
  • 對錶的插入和刪除等運算的效率較差。

三、線性表的鏈式存儲

1.定義

將線性表L=(a0,a1,……,an-1)中各元素分佈在存儲器的不同存儲塊,稱爲結點,每個結點(尾節點除外)中都持有一個指向下一個節點的引用,這樣所得到的存儲結構爲鏈表結構。

在這裏插入圖片描述

2.特點

  • 邏輯上相鄰的元素 ai, ai+1,其存儲位置也不一定相鄰;
  • 存儲稀疏,不必開闢整塊存儲空間。
  • 對錶的插入和刪除等運算的效率較高。
  • 邏輯結構複雜,不利於遍歷。

四、線性表、順序表、鏈表之間區別和聯繫

線性表:邏輯結構, 就是對外暴露數據之間的關係,不關心底層如何實現。

順序表、鏈表:物理結構,他是實際物理地址上的結構。比如順序表就是用數組實現。而鏈表用指針完成主要工作。不同的結構在不同的場景有不同的區別。

比如:對於java來說,大家都知道List接口類型,這就是邏輯結構,因爲他就是封裝了一個線性關係的一系列方法和數據,而具體的實現其實就是跟物理結構相關的內容。比如順序表的內容存儲使用數組的,然後一個get,set,add方法都要基於數組來完成。而鏈表是基於指針的,當我們考慮對象中的數據關係就要考慮指針的屬性,指針的指向和value。

對於一個線性表來說,不管它的具體實現方法如何,我們應該有的函數名稱和實現效果應該一致。你也可以感覺的到在一些結構的設計,比如List的Arraylist和LinkedList、Map的HashMap和currentHashMap他們的接口api都是相同的,但是底層設計實現肯定是有區別的。

所以,基於面向對象的編程思維,我們可以將線性表寫成一個接口,而具體實現的順序表和鏈表可以繼承這個接口的方法,提高程序的可讀性。

五、順序表

1.插入

add(int index,T t)

其中index爲插入的編號位置,t爲插入的數據

在這裏插入圖片描述
在這裏插入圖片描述

在這裏插入圖片描述

根據圖片你就很好理解插入操作。當插入一個index時候,他的後面所有元素都要後移一位。你可以看的出插入時候整個操作的臃腫性。所以這也是順序表性能表現最差的地方:頻繁的插入,刪除。

2.刪除

同理,刪除也是非常佔用資源的。原理和插入類似,不過人走了,空一個小板凳後面的人需要往前挪。

在這裏插入圖片描述

3.其他操作

其他操作就很簡單了。比如如果按照編號獲取數據getElem(int index),你可以直接根據數據座標返回。a[index],而其他操作,可以通過遍歷直接操作數組即可。

六、鏈表

1.指針

我想,表應該是很多人感覺很繞的東西,這個很大原因可能因爲指針。很多人說java沒指針,其實java他也有隱形指針。只不過不能直接用罷了。

指針建立的數據關係往往比數組這些要抽象的多。對於指針域,你把他當成一個對象就好了,不過這個對象指向的是另一個同等級對象。對於這個關係,你可以比作每個person類。每個person類都有老公(老婆),而這個老公老婆也是一個實際對象,可以理解這更像一種邏輯約定關係,而不是硬生生的關係吧。
在這裏插入圖片描述
指針你可以考慮成腦子記憶。上面的順序表我們說它有序因爲每個小板凳(數組)有編號,我們可以根據這個來確定位置。而對於鏈表來說,你可以看作成一個站在操場上的一隊人。而他的操作也略有不同,下面針對一些比較特殊和重要的進行歸納。

2.基本結構

對於線性表,我們只需要一個data數組和length就能表示基本信息。而對於鏈表,我們需要一個node(head頭節點),和length,當然,這個node也是一個結構體。

class node<T>{
    T data;//節點的結果
    node next;//下一個連接的節點
    public node(){}
    public node(T data)
    {
        this.data=data;
    }
    public node(T data, node next) {
        this.data = data;
        this.next = next;
    } 
}

當然,這個節點有數據域和指針域。數據域就是存放真實的數據,而指針域就是存放下一個node的指針。所以相比順序表,如果用滿數組情況下,鏈表佔用更多的資源,因爲它要存放指針佔用資源。

在這裏插入圖片描述

3.鏈表操作

  • 插入
    add(int index,T t) 其中index爲插入的編號位置,t爲插入的數據 加入插入一個節點node,根據index找到插入的前一個節點叫pre。

    操作流程爲:
    1.node.next=pre.next如下1的操作,將插入節點後面聯繫起來。此時node.next和pre.next一致。

    2.pre.next=node因爲我們要插入node,而node鏈可以替代pre自身的next。那麼直接將pre指向node。那麼就相當於原始鏈表插入了一個node。

在這裏插入圖片描述

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章