[程式設計題]劍指 Offer 09 用兩個棧實現佇列(四種方式[本質是2種方法])
阿新 • • 發佈:2020-07-20
lc 劍指 Offer 09. 用兩個棧實現佇列
題目描述
輸入輸出描述
思路
1、使用傳統的棧Stack即可完成
2、使用Deque資料結構堵住一端(堵住首)----(addLast(),removeLast) 或者堵住尾(addFirst();removeFirst)
3、使用Deque資料結構堵住一端(堵住尾(addFirst();removeFirst)
4、直接使用Deque模擬棧方法push,pop;即可 (其中就是底層使用的3的方法)
方法1:使用傳統的棧Stack即可完成
Java程式碼:
import java.util.Stack; public class Solution { Stack<Integer> stack1 = new Stack<Integer>(); Stack<Integer> stack2 = new Stack<Integer>(); public void push(int node) { stack1.push(node); } public int pop() { //pop的時候直接看棧2是否為空 if(stack2.isEmpty()){ while(!stack1.isEmpty()){ stack2.push(stack1.pop()); } //都存入棧2中的時候,呼叫一次pop方法,彈出一個stack2的棧頂元素(但是每次彈出都判斷棧是否空) if(!stack2.isEmpty()) { return stack2.pop(); }else { return -1; } }else{ //棧2不為空,直接彈出我們需要的棧頂元素(每次彈出每次檢測棧是否空) if(!stack2.isEmpty()) { return stack2.pop(); }else { return -1; } } } }
輸出:
時間和記憶體如下:
方法2:使用Deque資料結構堵住一端(堵住尾(addFirst();removeFirst)
相當於我們堵住雙端列表的尾部,從前邊存取。
addFirst();removeFirst)
如下:
Java程式碼
import java.util.*; public class Solution { Deque<Integer> stack1 = new LinkedList<>(); Deque<Integer> stack2 = new LinkedList<>(); public void push(int node) { stack1.addFirst(node); } public int pop() { //如果棧2空,先進行轉移操作 if(stack2.isEmpty()){ while(!stack1.isEmpty()){ stack2.addFirst(stack1.removeFirst()); } //把stack1元素都放入到stack2後可以彈出棧首,(每次都要檢測是否棧為空) if(!stack2.isEmpty()){return stack2.removeFirst();} else {return -1;} }else{ //棧2不為空 //彈出棧首,(每次都要檢測是否棧為空) if(!stack2.isEmpty()){return stack2.removeFirst();} else {return -1;} } } }
輸出:
方法3:使用Deque資料結構堵住一端(堵住首)----(addLast(),removeLast)
思想
addLast(),removeLast)
Java程式碼
import java.util.*; class CQueue { Deque<Integer> stack1; Deque<Integer> stack2; public CQueue() { stack1 = new LinkedList<Integer>(); stack2 = new LinkedList<Integer>(); } //Deque是雙端的佇列,我們只要保證一端不變就是棧,比如頭不變,往後插,從後取就是棧 public void appendTail(int value) { stack1.addLast(value); } public int deleteHead() { if(stack2.isEmpty()){ while(!stack1.isEmpty()){ stack2.addLast(stack1.removeLast()); } //放完之後取出stack2的最後的一個元素(因為模擬棧的話,統一看做First是堵住的) //注意出隊的時候一定要時刻判斷隊是否為空 if(!stack2.isEmpty()){return stack2.removeLast();}else{return -1;} }else{ //stack2不為空,就直接彈出 //注意出隊的時候一定要時刻判斷隊是否為空 if(!stack2.isEmpty()){return stack2.removeLast();}else{return -1;} } } }
方法4:直接使用Deque模擬棧方法push,pop;即可 (其中就是底層和方法2addFisrt原理相同)
java程式碼:
import java.util.*;
public class Solution {
Deque<Integer> stack1 = new LinkedList<Integer>();
Deque<Integer> stack2 = new LinkedList<Integer>();
public void push(int node) {
stack1.push(node);
}
public int pop() {
//如果棧2為空,就先轉移棧1元素如棧2
if(stack2.isEmpty()){
while(!stack1.isEmpty()){
stack2.push(stack1.pop());
}
//壓棧完成後,就可以本次的彈出操作(每次都要檢測本次出棧棧2空了嗎)
if(!stack2.isEmpty()){return stack2.pop();}
else return -1;
}else{
//如果棧2本身不為空,直接出棧
if(!stack2.isEmpty()){return stack2.pop();}
else return -1;
}
}
}
輸出: