【栈队列】两个栈实现一个队列、两个队列实现一个栈

两个栈实现一个队列

分析问题:栈的特性是后进先出,而队列的特性是先进先出,可以这样考虑,用其中一个栈作为辅助栈,栈s1,作为入队的栈,栈s2作为出队的辅助栈。
方法1、
入队:直接压入栈s1中,
出队:如果s1不为空的话,先把s1中的元素全部弹出压入s2中,s1为空的话,直接弹出s2的栈顶,注意:s1和s2都为空的话,那么队列为空。

template<class T>
class Queue
{
public:
    Queue(){}
    void Push(T data)
    {
        s1.push(data);
    }
    void Pop()
    {
        if(s1.empty()&& s2.empty())
            return ;
        else if(!s1.empty())
        {
            //将s1的内容弹出压入s2中
            s1Tos2();
            //弹出s2的栈顶
            s2.pop();
        }
        else//s1为空,s2不为空
        {
            //直接弹出s2栈顶
            s2.pop();
        }
    }
private:
    //将s1的内容弹出压入s2中
    void s1Tos2()
    {
        while(!s1.empty())
        {
            s2.push(s1.top());
            s1.pop();
        }
    }
private:
    statck<T> s1;//入队缓冲区
    statck<T> s2;//出队缓冲区
};

上述思路的优化???这是在网上看到的,我感觉不友好
就是上述出队的时候,将栈s1的内容弹出压入s2的时候,可以剩余1个,直接返回,这样可以减少一个s2压栈操作。

方法2、
其实就是方法1的变种
始终维护s1作为存储空间,以s2作为临时缓冲区,
入队时,将元素压入s1。
出队时,将s1的元素逐个“倒入”(弹出并压入)s2,将s2的顶元素弹出作为出队元素,之后再将s2剩下的元素逐个“倒回”s1。

方法3、
入队时,将元素压入s1。
出队时,判断s2是否为空,如不为空,则直接弹出顶元素;如为空,则将s1的元素逐个“倒入”s2,把最后一个元素弹出并出队。

其实上述方法都大同小异,都是基于一个思路。

两个队列实现一个栈

分析:两个队列,一个队列作为入栈的存储区,另一个队列作为中转站,但是不专职指定,那个队列为空就是入栈的存储,那个不为空的就是辅助中转站。
入栈:把元素放入不为空的队列,
出栈:把有元素的队列放置在队为空的栈中,最后一个元素不入队。

template<class T>
class Stack
{
public:
    Stack()
    {}
    void Push(T data)
    {
        if (!q1.empty())
        {
            q1.push(data);
        }
        else
        {
            q2.push(data);
        }
    }
    void Pop()
    {
        if (!q1.empty())
        {
            while (q1.size() != 0 && q1.size() != 1)
            {
                q2.push(q1.front());
                q1.pop();
            }
            q1.pop();
        }
        else
        {
            while (q2.size() != 0 && q2.size() != 1)
            {
                q1.push(q2.front());
                q2.pop();
            }
            q2.pop();
        }
    }
private:
    queue<T> q1;
    queue<T> q2;
};
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值