負margin原理及應用
劍指 Offer 09. 用兩個棧實現佇列
1、 問題描述
用兩個棧實現一個佇列。佇列的宣告如下,請實現它的兩個函式 appendTail 和 deleteHead ,
分別完成在佇列尾部插入整數和在佇列頭部刪除整數的功能。(若佇列中沒有元素,deleteHead 操作返回 -1 )
示例 1:
輸入:
[“CQueue”,“appendTail”,“deleteHead”,“deleteHead”]
[[],[3],[],[]]
輸出:
[null,null,3,-1]
示例 2:
輸入:
[“CQueue”,“deleteHead”,“appendTail”,“appendTail”,“deleteHead”,“deleteHead”]
輸出:
[null,-1,null,null,5,2]
提示:
1 <= values <= 10000
最多會對 appendTail、deleteHead 進行 10000 次呼叫
https://leetcode-cn.com/problems/yong-liang-ge-zhan-shi-xian-dui-lie-lcof/
2、 例項分析
兩個棧stack1 和stack2實現佇列,這道題的意圖是要求我們操作這兩個“先進後出”的棧實現一個“先進先出”的佇列CQueue。
我們通過一個具體的例子來分析往該佇列插入和刪除元素的過程。
首先插入–個元素a,不妨先把它插入到 stack1,此時stack1中的元素有{a},stack2為空。 再壓入兩個元素b和c,還是插入到stack1中,此時stack1中的元素有{a, b,c},其中c位於棧頂,而stack2仍然是空的(如圖(a)所示
從上面的分析中我們可以總結出刪除一個元素的步驟;當stack2中不為空時,在stack2中的棧頂元素是最先進入佇列的元素,可以彈出。如果stack2為空時,我們把stack1中的元素逐個彈出並壓入stack2。由於先進入佇列的元素被壓到stackl 的底端,經過彈出和壓入之後就處於stack2的頂端了,又可以直接彈出。
接下來再插入一個元素d。我們還是把它壓入stack1(如圖(d)所示),這樣會不會有問題呢?我們考慮下一次刪除佇列的頭部stack2不為空,直接彈出它的棧頂元素c (如圖 (e)所示)。而c的確是比d先進入佇列,應該在d之前從佇列中刪除,因此不會出現任何矛盾。
3、 分析總結
定義兩個stack,分別是stack1和stack2,佇列的push和pop是在兩側的,push操作很簡單,只需要在stack1上操作,而pop操作時,先將stack1的所有元素push到stack2中,然後stack2的pop返回的元素即為目標元素,只要stack2不為空下次刪除隊頭元素時可以從Stack2中直接出棧,只有當棧2為空棧1不為空時才將棧1的元素出棧壓入到棧2中。
4、python實現
class CQueue2:
def __init__(self):
self.stack1 = []
self.stack2 = []
def appendTail(self, value: int) -> None:
self.stack1.append(value)
def deleteHead(self) -> int:
if len(self.stack2)<=0: # 棧2為空迴圈--只有當棧2為空的時候才將棧1中的元素 壓入棧2中
while self.stack1: # 棧1不為空迴圈
self.stack2.append(self.stack1.pop()) # 棧1中的元素 壓入棧2中 棧1的棧底變成棧2的棧頂
if not self.stack2: # 如果棧1棧2都為空 則返回-1
return -1
else:
result = self.stack2.pop() # 當棧2為不空的時候,棧2的棧頂元素直接出棧
return result
# Your CQueue object will be instantiated and called as such:
obj = CQueue2()
obj.appendTail(1)
obj.appendTail(2)
obj.appendTail(3)
obj.appendTail(4)
param_2 = obj.deleteHead()
print(param_2)
param_2 = obj.deleteHead()
print(param_2)
param_2 = obj.deleteHead()
print(param_2)
param_2 = obj.deleteHead()
print(param_2)
param_2 = obj.deleteHead()
print(param_2)
obj.appendTail(1)
obj.appendTail(2)
obj.appendTail(3)
obj.appendTail(4)
param_2 = obj.deleteHead()
print(param_2)
param_2 = obj.deleteHead()
print(param_2)