剑指offer 编程题(5):两个栈实现队列,两个队列实现栈

来源:互联网 发布:windows date 编辑:程序博客网 时间:2024/06/05 14:07

问题1:用两个栈实现一个队列,实现队列的push和delete操作 
栈的特性是先进后出(FILO),队列的特性是先进先出(FIFO),在实现delete时,我们的难点是如何将栈中最底层的数据拿出来,我们有两个栈,所以我们可以将一个栈中的数据依次拿出来压入到另一个为空的栈,另一个栈中数据的顺序恰好是先压入栈1的元素此时在栈2的上面,为了实现效率的提升,我们在delete时,判断栈2是否有数据,如果有的话,直接删除栈顶元素,在栈2为空时才将栈1的数据压入到栈2中,从而提高程序的运行效率,实现过程可以分为下面几个步骤: 
1、push操作时,一直将数据压入到栈2中 
2、delete操作时,首先判断栈2是否为空,不为空的情况直接删除栈2栈顶元素,为空的话将栈1的数据压入到栈2中,再将栈2栈顶元素删除。 
实现代码如下:

template <typename T>class CQueue{public:    CQueue(void)    {}    ~CQueue(void)    {}    void appendTail(const T& node);    T deleteHead();private:    stack<T> stack1;    stack<T> stack2;};template<class T>void CQueue<T>::appendTail(const T& node)//在队列尾部添加数据{    stack1.push(node);}template<class T>T CQueue<T>::deleteHead(){    T tmp = 0;    if (stack2.empty()) //若栈2为空    {        while (!stack1.empty())        {            tmp = stack1.top();            stack2.push(tmp);            stack1.pop();        }    }    tmp = stack2.top();    stack2.pop();    return tmp;}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37

运行结果如下:

问题2:用两个队列实现一个栈 
因为队列是先进先出,所以要拿到队列中最后压入的数据,只能每次将队列中数据pop到只剩一个,此时这个数据为最后压入队列的数据,在每次pop时,将数据压入到另一个队列中。每次执行delete操作时,循环往复。(感觉效率低)每次删除时间复杂度O(N) 
代码如下:

template <typename T>class CStack{public:    CStack(void)    {}    ~CStack(void)    {}    void appendTail(const T& node);    T deleteHead();private:    queue<T> q1;    queue<T> q2;};template<class T>void CStack<T>::appendTail(const T& node)//在栈尾部添加数据{    if (!q1.empty())//不为空的执行push操作    {        q1.push(node);    }    else    {        q2.push(node);    }}template<class T>T CStack<T>::deleteHead(){    int ret = 0;    if (q1.empty())    {        int i = q2.size();        while (i > 1 )//将q2队列中的数据pop到只剩一个        {            q1.push(q2.front());            q2.pop();            --i;        }        ret = q2.front();        q2.pop();    }    else    {        int i = q1.size();        while (i > 1)        {            q2.push(q1.front());            q1.pop();            --i;        }        ret = q1.front();        q1.pop();    }    return ret;
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56

两个问题解决思路类似,主要就是要合理使用队列和栈的特点,并注意程序的效率。


用两个栈实现一个队列的功能?要求给出算法和思路!

<分析>:

入队:将元素进栈A

出队:判断栈B是否为空,如果为空,则将栈A中所有元素pop,并push进栈B,栈B出栈;

 如果不为空,栈B直接出栈。

用两个队列实现一个栈的功能?要求给出算法和思路!

<分析>:

入栈:将元素进队列A

出栈:判断队列A中元素的个数是否为1,如果等于1,则出队列,否则将队列A中的元素  以此出队列并放入队列B,直到队列A中的元素留下一个,然后队列A出队列,再把  队列B中的元素出队列以此放入队列A中。