用两个栈实现队列
题目:
用两个栈实现一个队列。队列的声明如下,请实现它的两个函数appendTail和deleteHead,分别完成在队列尾部插入节点和在队列头部删除节点的功能
template<typename T>class CQueue
{
public:
CQueue(void);
~CQueue(void);
void appendTail(const T& node);
T deleteHead();
private:
stack<T>stack1;
stack<T>stack2;
}
用两个栈,如何模拟出队列两个操作,我们可以这模拟一个动态的过程来进行观察。
1、开始队列为空,需要将一个节点a添加到队列中
因为一开始队列是空的,也就是两个队列都是空的,我们假设将到来的节点放入栈stack1中
2、b,c节点依次到来,加入队列中
因为现在还是单纯的添加,此时还不需要运用栈stack2中,所以还是直接插入栈中
3、然后需要将最先加入的a从队列中删除
因为a是最先加入的,因此需要删除a,但是a在stack1的最下面,所以不能直接删除,此时可以借助stack2了。
先将stack1中的节点依次弹出,放入stack2中,此时stack2中的顺序就是正常队列的顺序了,只需要将stack2中的顶部元素pop掉,就达到删除功能了
通过以上分析可以发现:
stack2其实是维护着队列的真实状态,stack1更像是一个缓冲区,先将新到来的节点放入stack1中,如果要删除节点,就删除stack2的的顶部节点,如果stack2为空,就将缓冲区stack1中的元素放入stack2中,再进行操作。这样队列的模拟就完成了。
代码:
template<typename T>void CQueue<T>::appendTail(const T& element)
{
stack1.push(element);
}
template<typename T>void CQueue<T>::deleteHead()
{
if(stack2.size()<=0)
{
while(stack1.size()>0)
{
T& data=stack1.top();
stack1.pop();
stack2.push(data);
}
}
if(stack.size()==0) throw new exception("queue is empty");
T head=stack2.top();
stack2.pop();
return head;
}
——————————————————————————————————————————————————
参考书籍: 《剑指offer 第二版》