棧是一種操作受限的線性表,只支援在一端進行插入和刪除操作(入棧和出棧)。後進先出、先進後出是它最大的特點。當某個資料集合只在一端插入和刪除資料,並滿足先進後出的特性時,就可以選擇棧這種資料結構。
棧既可以通過陣列實現,也可以通過連結串列來實現。用陣列實現的棧,我們叫作順序棧,用連結串列實現的棧,我們叫作鏈式棧。不管基於陣列還是連結串列,入棧、出棧的時間複雜度都為 O(1)。
class stack {
private $size;
private $top = -1;
private $stack = array();
public function __construct( $size ){
$this->size = $size ;
}
#判斷棧是否為空
public function isEmpty() {
return ( $this->top == -1 ? true : false ) ;
}
#判斷棧是否已滿
public function isFull(){
return ( $this->top < $this->size-1 ? false : true);
}
#入棧
public function pushStack( $data ) {
if( $this->isFull() ){
return false;
}
$stack[] = $data;
$top++;
return true;
}
#出棧
public function popStack(){
if( $this->isEmpty() ){
return false;
}
unset( $stack[ $top ] );
$top--;
return true;
}
}
基於棧結構對資料存取採用 " 先進後出、後進先出 " 原則的特點,它可以用於實現很多功能。
1,瀏覽器的回退、前進功能。
2,括號匹配問題。
3,數值的進位制轉換功能。
拿括號匹配做個例子:
這裡我們假設只有圓括號、方括號和花括號。{[](){}}或 [{()}] 等是合規的格式,而 {[}()] 為不合規的格式。
- 從左向右依次掃描字串,當掃描到左括號時,將其入棧;
- 當掃描到右括號時,從棧頂取出左括號。如果匹配,則繼續掃描字串。如果不匹配或棧空,說明是不合規格式。
- 當字串掃描結束,如果棧空,則是合規字元。如果棧不空,則是不合規格式。
額外說下瀏覽器的前進和後退功能。
我們可以使用兩個棧,m 和 n,將瀏覽的頁面依次壓入棧 m中。當點選後退按鈕時,依次從棧 m 中出棧,並依次放入棧 n 中。當我們點選瀏覽器的前進按鈕時,我們依次從棧 n 中取出資料,放入棧 m 中。當棧 m 中沒有資料時,那就說明沒有頁面可以繼續後退瀏覽了。當棧 n 中沒有資料,那就說明沒有頁面可以點選前進按鈕瀏覽了。這樣,瀏覽器的前進和後退功能就實現了。