5. 用两个队列实现一个栈

本文详细介绍了如何利用两个队列来模拟栈的操作,包括压栈、弹栈、获取栈顶元素等,通过代码示例展示了具体的实现过程。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

  • 压栈操作直接用队列的enqueue操作模拟。这道题的难点在于如何模拟出栈操作。

    队列中的元素只有在成为队头后才有资格被dequeue操作删掉,那么这道题其实是在问,如何把一个队列的队尾移动到队头位置,删除它之后,其他元素可以按原顺序放回?把队列A的元素依次出队,并送入队列B,直到队列A中只剩下一个元素,它既是队尾又是队头,把它出队后,在反过来把队列B中元素依次出队,并送回队列A。这便是把队列A队尾元素删掉的过程。

#include "queue.h"
template<typename Object>
class StackByQueues
{
public:
    StackByQueues()
    {
        for(int i = 0; i != NUM; ++i)
            pQueue[i] = new Queue<Object>;
    }

    StackByQueues(const StackByQueues& rhs)
    {
        for(int i = 0; i != NUM; ++i)
            pQueue[i] = new Queue<Object>(*(rhs.pQueue[i]));
    }
    StackByQueues(StackByQueues&& rhs)
    {
        for(int i = 0; i != NUM; ++i)
        {
            pQueue[i] = rhs.pQueue[i];
            rhs.pQueue[i] = nullptr;
        }
    }
    StackByQueues& operator =(const StackByQueues& rhs)
    {
        auto copy(rhs);
        for(int i = 0; i != NUM; ++i)
            std::swap(this->pQueue[i], copy.pQueue[i]);
        return *this;
    }
    StackByQueues& operator =(StackByQueues&& rhs)
    {
        for(int i = 0; i != NUM; ++i)
            std::swap(this->pQueue[i], rhs.pQueue[i]);
        return *this;
    }
    ~StackByQueues()
    {
        for(int i = 0; i != NUM; ++i)
        {
            if(pQueue[i])
                delete pQueue[i];    //注意:这里不能写成 delete pQueue;
        }
    }
    void push(const Object& object)
    {
        if(pQueue[0]->full())
            std::cout << "overflow" << std::endl;
        else
            pQueue[0]->enqueue(object);
    }
    void push(Object&& object)
    {
        if(pQueue[0]->full())
            std::cout << "overflow" << std::endl;
        else
            pQueue[0]->enqueue(std::move(object));
    }
    Object top()
    {
        if(pQueue[0]->empty())
        {
            std::cout << "underflow" << std::endl;
            return Object();
        }
        else
        {
            return pQueue[0]->tail();
        }
    }
    void pop()
    {
        if(pQueue[0]->empty())
            return;
        auto size = pQueue[0]->getSize();    //注意:写循环语句时要注意,条件变量值是否会被循环体修改,例如这里的getSize()
        for(int i = 0; i != size-1; ++i)
            pQueue[1]->enqueue(pQueue[0]->dequeue());

        pQueue[0]->dequeue();

        size = pQueue[1]->getSize();
        for(int i = 0; i != size; ++i)
            pQueue[0]->enqueue(pQueue[1]->dequeue());
    }

    bool empty() const{return pQueue[0]->empty();}
    bool full() const {return pQueue[0]->full();}
private:
    static constexpr int NUM = 2;
    Queue<Object>* pQueue[NUM];
};

void testStackByQueues()
{
    using namespace std;
    struct Student
    {
        char name[10];
        int  age;
    };
    constexpr int NUM = 5;
    Student students[NUM] = {Student{"Tom", 12},Student{"Micheal", 13},
                          Student{"Anna", 14},Student{"Lily", 10},
                          Student{"James", 19}};
    StackByQueues<Student> s;
    for(int i = 0; !s.full() && i != NUM; ++i)
        s.push(students[i]);

    decltype(s) s_copy(s);
    decltype(s_copy) s_move(std::move(s_copy));

    while(!s_move.empty())
    {
        auto stu = s_move.top();
        s_move.pop();
        cout << "name: " << stu.name << " age: " << stu.age << endl;
    }
}

/*test output:
name: Lily age: 10
name: Anna age: 14
name: Micheal age: 13
name: Tom age: 12
*/

随笔《栈和队列的数组实现》给出了queue.h的实现

转载于:https://www.cnblogs.com/meixiaogua/p/10173765.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值