原文是在我本身博客中,小夥伴也能夠點 閱讀原文進行跳轉查看,還有好聽的背景音樂噢背景音樂已取消~ 2333333
什麼是線性表?就是一種連續或間斷存儲的數組,這裏的連續和間斷是針對物理內存空間中線性表元素之間是否連續,其中連續數組對應內置數組的實現方式,間斷數組對應的是指針的實現方式,這種方式也稱爲鏈表實現。php
也就是說,線性表有兩種實現方式,一種是內置數組實現,另外一種是鏈表實現。
下面來看一下,有哪些數據結構屬於線性表吧!html
棧(stack)又名堆棧,它是一種運算受限的線性表。其限制是 僅容許在表的一端進行插入和刪除運算。這一端被稱爲棧頂,相對地,把另外一端稱爲棧底。向一個棧插入新元素又稱做進棧、入棧或壓棧,它是把新元素放到棧頂元素的上面,使之成爲新的棧頂元素;從一個棧刪除元素又稱做出棧或退棧,它是把棧頂元素刪除掉,使其相鄰的元素成爲新的棧頂元素。
經過上面的話語表達,相信不難理解棧的概念。下面咱們上圖感覺一下棧和入棧出棧狀況:算法
上圖中咱們能夠看到入棧、出棧的實際狀況。只有一個入口(缺口),在這個缺口處,進行入棧和出棧操做。在現實生活中更形象的比喻就是壘磚。
磚一次一次往上疊加,取的時候也是從最上部取,一直取到底部的最後一塊。數組
php也能夠實現簡單的棧,因爲php中沒有提供很好的操做指針的方式,因此只能經過數組的方式實現。使用連個函數就能夠,它們分別是 array_push和array_pop數據結構
array_push
將一個或多個單元壓入數組的末尾(入棧);array_pop
彈出數組最後一個單元(出棧)簡單代碼示例:函數
$arr = []; array_push($arr, 1); // $arr[] = 1; print_r($arr); sleep(1); array_push($arr, 2); // $arr[] = 2; print_r($arr); sleep(1); array_push($arr, 3); // $arr[] = 3; print_r($arr); sleep(1); $val = array_pop($arr); echo $val . "\n\n"; print_r($arr); sleep(1); $val = array_pop($arr); echo $val . "\n\n"; print_r($arr);
把這段代碼放在cli下跑,就能看到效果了,看一下運行gif圖:spa
從命令行的執行結果來看,咱們先依次入棧一、二、3三個值,後來取出的時候,也是按照棧的先進後出,後進先出的特性出棧的。.net
隊列(queue)是一種採用先進先出(FIFO)策略的抽象數據結構,它的想法來自於生活中排隊的策略。在生活中比較形象的比喻就是排隊了。
一樣的,php中也能夠以數組的形式實現隊列,兩個函數array_push和array_shift命令行
能夠發現array_push和上面的棧入棧是同一個函數,其實兩個函數的做用同樣。用在這裏就表示爲入隊了。指針
簡單代碼示例:
header("Content-type:text/html;charset=utf-8"); $arr = []; echo '入隊-1 array_push($arr, 1)' . "\n"; array_push($arr, 1); // $arr[] = 1; print_r($arr); sleep(1); echo '入隊-2 array_push($arr, 2)' . "\n"; array_push($arr, 2); // $arr[] = 2; print_r($arr); sleep(1); echo '入隊-3 array_push($arr, 2)' . "\n"; array_push($arr, 3); // $arr[] = 3; print_r($arr); sleep(1); echo '出隊-3 array_shift($arr)' . "\n"; $val = array_shift($arr); echo $val . "\n\n"; print_r($arr); sleep(1); echo '出隊-2 array_shift($arr)' . "\n"; $val = array_shift($arr); echo $val . "\n\n"; print_r($arr);
圖示:
從命令行的執行結果咱們能夠看到,咱們依次入隊 一、二、3三個值,出隊的時候先出1,再出2.符合咱們隊列的特性,先進先出,後進後出。
*next
)單鏈表是一種鏈式存取的數據結構,用一組地址任意的存儲單元存放線性表中的數據元素。鏈表中的數據是以結點來表示的,每一個結點的構成:元素(數據元素的映象) + 指針(指示後繼元素存儲位置),元素就是存儲數據的存儲單元,指針就是鏈接每一個結點的地址數據
鏈表有兩個比較重要的部分組成:
圖中咱們能夠看到,單向鏈表由一個頭指針、頭節點、n個元素節點和尾節點組成。
其中頭指針表明,咱們根據這個指針能夠找到對應的鏈表
頭節點,用來存儲鏈表的一些信息,好比鏈表長度,頭節點指針指向第一個元素節點
每一個節點中又包括,節點數據(data)和指針(*next指向下一個元素節點)、
一直到尾節點爲null
data
)以外的上一個節點的指針(*prev
)和下一個節點的指針(*next
)雙向鏈表又叫作雙鏈表;跟單向鏈表不一樣的是,他的每一個節點都有兩個指針,一個指向前面的一個節點,一個指向後面的節點。經過這兩個指針咱們能夠很方便的經過某一個節點,訪問到相(前)鄰(後)的兩個節點。
咱們來看一下,雙向鏈表的圖示:
圖中咱們能夠看到,除了頭節點和尾節點以外,每一箇中間節點與節點之間都是首尾相連,每一個節點保存了上一個節點的指針和下一個節點的指針,這就是與單鏈表的不一樣之處。
注:咱們也能夠構造雙向循環鏈表;尾節點的下一個指針*next
指向頭節點,而頭節點的*prev
指向尾節點;這樣就構成了一個雙向循環鏈表;下圖所示,咱們只需把雙向鏈表簡單改造一下便可:
以上,就是本篇文章介紹的內容了。數據結構不少,也很高深,其中的算法知識,也讓人耐人尋味。