栈和队列相互实现(Java)

news2024/11/24 20:11:37

本篇任务

前篇我们分别介绍了栈和队列,并对其进行了简单的自我实现,本篇我们将通过栈和队列的相互实现来进一步熟悉和运用栈和队列,如下是我们将要完成的题目:

用队列实现栈icon-default.png?t=O83Ahttps://leetcode-cn.com/problems/implement-stack-using-queues/

用栈实现队列icon-default.png?t=O83Ahttps://leetcode-cn.com/problems/implement-queue-using-stacks/

问题描述

  实现 MyQueue 类和 MyStack 类::

  • void push(int x) 将元素 x 推到队列的末尾
  • int pop() 从队列的开头移除并返回元素
  • int peek() 返回队列开头的元素
  • boolean empty() 如果队列为空,返回 true ;否则,返回 false

  说明:

  • 你只能使用标准的栈操作 —— 也就是只有 push to top, peek/pop from topsize, 和 is empty 操作是合法的。
  • 你所使用的语言也许不支持栈。你可以使用 list 或者 deque(双端队列)来模拟一个栈,只要是标准的栈操作即可。

     不论是用队列模拟栈,还是用栈模拟队列,我们都会发现使用 poll 方法取出元素时,栈 Stack 从顶部取出即 34 ,而队列则从队头取出 12

原因分析:

        使用一个栈来模拟队列时,所有元素都会被推入栈中,这意味着后入栈的元素会先出栈,与队列的先进先出特性不符。使用一个队列模拟栈时情况于此相反。那么如何解决这个问题呢?。


解决方案:


        为了实现队列的先进先出(FIFO)特性,我们通常会使用两个栈来模拟队列。一个栈用于入队操作,将元素按顺序推入栈中。另一个栈用于出队操作,当需要出队时,将入队栈中的元素依次弹出并推入出队栈中,然后从出队栈中弹出元素即可实现队列的先进先出特性。

        创建两个栈,Queue1 和 Queue2 ,向栈中添加元素时,同样向 Queue1 中添加,当模拟出栈操作时,将 Queue1 队列中除了最后一个元素之外的所有元素,逐个出队并入队到 Queue2 队列中。然后将 Queue1 队列中的最后一个元素出队,即为栈Q顶元素。

    其余操作依次类推,将数据不断在 Queue1 和 Queue2 中转换即可,代码实现如下: 

public class MyStackByQueue {
        public Queue<Integer> que1;
        public Queue<Integer> que2;
        public MyStackByQueue() {
            que1=new LinkedList<>();
            que2=new LinkedList<>();
        }

        public void push(int x) {
            if(!que1.isEmpty()) {
                que1.offer(x);
            }else if(!que2.isEmpty()) {
                que2.offer(x);
            }else {
                que1.offer(x);
            }
        }

        public int pop() {
            if(empty()){
                return -1;
            }
            if(!que1.isEmpty()){
                int size= que1.size()-1;
                for(int i=0;i<size;i++){
                    que2.offer(que1.poll());
                }
                return que1.poll();
            }else{
                int size=que2.size()-1;
                for(int i=0;i<size;i++){
                    que1.offer(que2.poll());
                }
                return que2.poll();
            }
        }

        public int top() {
            int val=0;
            if(empty()){
                return -1;
            }
            if(!que1.isEmpty()){
                int size=que1.size();
                for(int i=0;i<size;i++){
                    val=que1.poll();
                    que2.offer(val);
                }
                return val;
            }else{
                int size= que2.size();
                for(int i=0;i<size;i++){
                    val=que2.poll();
                    que1.offer(val);
                }
                return val;
            }
        }

        public boolean empty() {
            return que1.isEmpty()&&que2.isEmpty();
        }
    }

        为了满足栈的后进先出(FOFI)Q的特性,通常使用两个队列实现栈Q。入栈操作时,将元素添加到非空的队列末尾;出栈操作时,将非空队列中的元素逐个取出并加入空队列,直到取出待出栈元素,然后将非空队列和空队列的角色互换,以便下一次操作。这样就可以实现栈的后进先出的效果

        定义两个链栈Stack1和Stack2,其中Stack1用于入队操作,Stack2用于出队操作。入队操作时,直接将元素压入Stack1即可。出队操作时,首先判断Stack2是否为空。若不为空,则直接弹出Stack2的栈顶元素即为出队元素;若为空,则将Stack1中的所有元素逐个弹出并压入Stack2,然后弹出Stack2的栈顶元素。

  代码实现如下: ( top() 换为 peek()

public class MyQueueByStack {
    public Deque<Integer> st1;
    public Deque<Integer> st2;
    public MyQueueByStack() {
        st1=new LinkedList<>();
        st2=new LinkedList<>();
    }

    public void push(int x) {
        st1.offer(x);
    }

    public int pop() {
        if(empty()){
            return -1;
        }
        if(!st1.isEmpty()){
            int size=st1.size();
            for(int i=0;i<size;i++){
                st2.offer(st1.poll());
            }
        }
        return st2.poll();
    }

    public int peek() {
        if(empty()){
            return -1;
        }
        if(!st1.isEmpty()){
            int size=st1.size();
            for(int i=0;i<size;i++){
                st2.offer(st1.poll());
            }
        }
        return st2.peek();
    }

    public boolean empty() {
        return st1.isEmpty()&&st2.isEmpty();
    }
}

      到这里本篇就圆满完成!有问题或不懂之处欢迎在评论区提出

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/2188129.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

【2022工业图像异常检测文献】CFLOW-AD: 通过条件归一化流实现实时无监督定位异常检测

CFLOW-AD: Real-Time Unsupervised Anomaly Detection with Localization via Conditional Normalizing Flows 1、Background 虽然最近提出针对此类数据设置的模型在准确性指标上取得了很高的成绩&#xff0c;但它们的复杂性限制了实时处理的能力。 CFLOW-AD由一个经过判别式…

区块链+Web3学习笔记

学习资料来源于B站&#xff1a; 17小时最全Web3教程&#xff1a;ERC20&#xff0c;NFT&#xff0c;Hardhat&#xff0c;CCIP跨链_哔哩哔哩_bilibili 该课程提供的Github代码地址&#xff0c;相关资料详见README.md&#xff1a; Web3_tutorial_Chinese/README.md at main sm…

Netty系列-8 Netty处理粘包和半包问题

1.半包和粘包问题 TCP协议是基于字节流的数据通讯协议&#xff0c;数据被看做是一连串的字节流&#xff1b;不具备边界信息&#xff0c;给接收方带来半包和粘包问题。 半包&#xff1a;TCP传输时&#xff0c;将数据切割成一个个数据包进行传输。接收方一次读取操作&#xff0c…

吉他弹唱打谱软件哪个好用 吉他弹唱制谱教程

吉他这门乐器一直受到大众的欢迎&#xff0c;究其原因&#xff0c;还是因为其成本低廉、易上手的特性。但是吉他是一个入门容易精通难的乐器&#xff0c;想要成为一个资深的吉他玩家&#xff0c;那么就少不了用到一些吉他弹唱打谱软件。今天我们就来说一说吉他弹唱打谱软件哪个…

学习 CSS 新的属性 conic-gradient 实现环形进度条

我们在工作中用到环形进度条的时候&#xff0c;一般都是使用组件库提供的&#xff0c;那么你有没有想过这是怎么实现的呢&#xff1f; <divclass"progress"style"--progress: 80%; --last: 20%"data-progress"80%"></div><style …

【宽搜】2. leetcode 102 二叉树的层序遍历

题目描述 题目链接&#xff1a;二叉树的层序遍历 根据上一篇文章的模板可以直接写代码&#xff0c;需要改变的就是将N叉树的child改为二叉树的left和right。 代码 class Solution { public:vector<vector<int>> levelOrder(TreeNode* root) {vector<vector&…

k8s的学习和使用

为什么用k8s&#xff0c;不用docker&#xff1f; k8s更适合复杂的微服务架构和大规模的容器应用。 Pods(Pod) Pod是k8s最小可部署单元&#xff0c;他包含一个或多个相关容器。这些容器共享网络命名空间和存储卷&#xff0c;他们通常协同工作来构成一个应用程序。 Serv…

开启AI新篇章:探索GPT-4与大模型!订阅方案!简单支付!

开启AI新篇章&#xff1a;探索GPT-4的无限可能 随着人工智能技术的飞速发展&#xff0c;我们正处于一个前所未有的变革时代。作为人工智能领域的领导者&#xff0c;OpenAI 推出的GPT-4&#xff0c;以其卓越的自然语言处理能力和强大的计算潜力&#xff0c;引发了行业内外的广泛…

深入浅出MySQL

深入浅出MySQL 以下内容参考自 《MySQL是怎样运行的&#xff1a;从根儿上理解MySQL》一书&#xff0c;强烈推荐 存储引擎 对于不同的表可以设置不同的存储引擎 CREATE TABLE tableName (xxxx ) ENGINE 引擎名称; # 修改 ALTER TABLE tableName ENGINE xxx; 编码格式 my…

(C语言贪吃蛇)10.贪吃蛇向右自行行走

目录 前言 本节内容 实现效果 修改后的代码 其他封装函数&#xff1a; 运行效果 总结 前言 我们上节讲解了关于贪吃蛇撞墙然后死翘翘重新初始化蛇身的操作&#xff0c;主要是关于程序初始化释放内存的操作&#xff0c;不理解的再去看看&#x1f618;(贪吃蛇撞墙找死详解)。…

SpringBoot技术栈:构建高效古典舞交流平台

第二章 相关技术介绍 2.1Java技术 Java是一种非常常用的编程语言&#xff0c;在全球编程语言排行版上总是前三。在方兴未艾的计算机技术发展历程中&#xff0c;Java的身影无处不在&#xff0c;并且拥有旺盛的生命力。Java的跨平台能力十分强大&#xff0c;只需一次编译&#xf…

openpnp - 吸嘴校正失败的opencv参数分析

文章目录 openpnp - 吸嘴校正失败的opencv参数分析概述笔记阶段验证 - N2吸嘴校验完NT1NT2 阶段验证 - 底部相机高级校验完NT1NT2 参数比对保存 “阶段验证 - N2吸嘴校验完” 的NT1/NT2图像重建参数检测环境NT1ok的3个参数值NT1err的3个参数值NT2ok的3个参数值NT2err的3个参数值…

如何入门运动规划算法? 50篇教程教你手把手推导公式! 实现代码!

经常听到有想入门规划算法的同学说: 各路教程不成体系, 不知从何学起? 网上的规划算法教程资料确实很多. 但是东一篇frenet, 西一篇QP优化, 大部分都是各路大佬写给自己看的学习笔记, 杂乱无章不成体系. 有没有给小白看的, 完整成体系的运动规划算法教程呢? 穷学生囊中羞…

Redis入门第四步:Redis发布与订阅

欢迎继续跟随《Redis新手指南&#xff1a;从入门到精通》专栏的步伐&#xff01;在本文中&#xff0c;我们将深入探讨Redis的发布与订阅&#xff08;Pub/Sub&#xff09;模式。这是一种强大的消息传递机制&#xff0c;适用于各种实时通信场景&#xff0c;如聊天应用、实时通知和…

反调试—1

IsDebuggerPresent() CheckRemoteDebuggerPresent() 其内部实际调用NtQueryInformationProcess() bool _stdcall ThreadCall() {while (true){BOOL pbDebuggerPresent FALSE;CheckRemoteDebuggerPresent(GetCurrentProcess(), &pbDebuggerPresent);if (pbDebuggerPres…

Redis数据库与GO(一):安装,string,hash

安装包地址&#xff1a;https://github.com/tporadowski/redis/releases 建议下载zip版本&#xff0c;解压即可使用。解压后&#xff0c;依次打开目录下的redis-server.exe和redis-cli.exe&#xff0c;redis-cli.exe用于输入指令。 一、基本结构 如图&#xff0c;redis对外有个…

Netgear-WN604 downloadFile.php 信息泄露复现(CVE-2024-6646)

0x01 产品描述&#xff1a; NETGEAR WN604是一款功能强大的双频AC1200无线路由器,非常适合中大型家庭和企业使用。它支持最新的802.11ac无线标准,能提供高达1200Mbps的无线传输速度。路由器具备千兆有线网口和3个100Mbps有线网口,可满足有线和无线设备的接入需求。此外,它还内置…

详解JavaScript中函数式编程

函数式编程 JS并非函数式编程语言&#xff0c;但可以应用函数式编程技术&#xff0c;这种风格很多语言都用&#xff0c;例如Java. 使用函数处理数组 假设有一个数组&#xff0c;数组元素都是数字&#xff0c;我们想要计算这些元素的平均值和标准差。使用非函数式编程风格的话…

vue基于springboot的促销商城购物管理系统带抽奖dm8o6

目录 功能介绍系统实现截图开发工具合计数介绍技术介绍核心代码部分展示可行性分析springboot文件解析详细视频演示源码获取 功能介绍 用户功能 注册登录&#xff1a;允许用户创建账户和登录系统。 个人中心&#xff1a;用户可以查看和编辑个人信息&#xff0c;密码、联系方式…

RabbitMQ篇(死信交换机)

目录 一、简介 二、TTL过期时间 三、应用场景 一、简介 当一个队列中的消息满足下列情况之一时&#xff0c;可以成为死信&#xff08;dead letter&#xff09; 消费者使用basic.reject或者basic.nack声明消费失败&#xff0c;并且消息的requeue参数设置为false消息是一个过…