当前位置: 首页 > article >正文

栈(Stack)和队列(Deque、Queue)

文章目录

  • 一、栈
    • 1.1 栈 VS 虚拟机栈 VS 栈帧
    • 1.2 数据结构 -- 栈介绍
    • 1.3 用数组模拟实现栈
    • 1.4 栈的功能:逆序打印
  • 二、队列
    • 2.1 数据结果 -- 队列介绍
    • 2.2 用单链表模拟实现Queue队列

一、栈

1.1 栈 VS 虚拟机栈 VS 栈帧

  1. 区别
    • :是一种数据结构
      • 任何数据结构都是用来组织描述数据的
    • 虚拟机栈(JVM虚拟机栈):是系统的一块内存
    • 栈帧:方法调用的时候,在虚拟机栈上开辟的内存区域

1.2 数据结构 – 栈介绍

  1. 栈的特点:只允许在固定的一端进行插入和删除元素操作,且是先进后出的
    在这里插入图片描述
  2. Java中如何使用栈
    • Stack<类型> stack = new Stack<>();
    • 上述方法用得越来越少了,现在多用【ArrayDequeue】代替
  3. 栈是如何实现的
    在这里插入图片描述
  4. 关于模拟实现栈:可以用数组/链表,Java中的Stack底层是用数组实现的
    • 用数组实现:看下面
    • 用链表实现
      在这里插入图片描述

1.3 用数组模拟实现栈

  1. 实现结构
    • 此处设计是整型数组
    • 使用usedSize记录当前有序的数据,插入元素时可以把它当成下标
  2. 添加元素 push():如果数组满了需要扩容
  3. 删除元素 pop():栈不为空时才出元素
  4. 获取栈顶元素 peek():栈不为空时才能获取
public class MyStack {
    private int[] elem;
    private int usedSize;

    public MyStack() {
        this.elem = new int[5];
    }

    //压栈 --- 放元素
    public void push(int val) {
        if(isFull()) {
           elem = Arrays.copyOf(elem,2*elem.length);
        }
        elem[usedSize] = val;
        usedSize++;
    }

    public boolean isFull() {
        return usedSize == elem.length;
    }


    //出栈
    public int pop() {
        if(empty()) {
            throw new StackEmptyException("栈为空!");
        }
        return elem[--usedSize];
    }

    //获取栈顶元素
    public int peek() {
        if(empty()) {
            throw new StackEmptyException("栈为空!");
        }
        
        return elem[usedSize-1];
    }

    public boolean empty() {
        return usedSize == 0;
    }
}

//这是设计的自定义异常
public class StackEmptyException extends RuntimeException{
    public StackEmptyException() {
    }

    public StackEmptyException(String message) {
        super(message);
    }
}

1.4 栈的功能:逆序打印

  1. 解析:如果我们要将一个递归实现的代码改成非递归,基本会用到栈/队列
  2. 代码
    在这里插入图片描述

二、队列

2.1 数据结果 – 队列介绍

  1. 队列特点:只允许在一端进行插入数据操作,在另一端进行删除数据操作的特殊线性表,且是先进先出

  2. Java中如何使用队列

    • Deque 双端队列
      在这里插入图片描述

    • Queue 队列
      在这里插入图片描述

  3. 关于Queue队列的模拟实现:数组和链表都可以实现

    • 用数组实现
      在这里插入图片描述
      在这里插入图片描述

    • 用链表实现
      在这里插入图片描述

2.2 用单链表模拟实现Queue队列

public class MyQueue {
    public ListNode head;
    public ListNode last;
    static class ListNode {
        public int val;
        public ListNode next;

        public ListNode(int val) {
            this.val = val;
        }
    }
    
    private int usedSize;

    public void offer(int val) {
        ListNode node = new ListNode(val);
        if(head == null) {
            head = node;
            last = node;
        }else {
            last.next = node;
            last = last.next;
        }
        usedSize++;
    }

    public int getUsedSize() {
        return usedSize;
    }

    public int poll() {
        if(head == null) {
            return -1;
        }
        int val = -1;
        if(head.next == null) {
            val = head.val;
            head = null;
            last = null;
            return val;
        }
        val = head.val;
        head = head.next;
        usedSize--;
        return val;
    }

    public int peek() {
        if(head == null) {
            return -1;
        }
        return head.val;
    }

}


http://www.kler.cn/a/389102.html

相关文章:

  • 测试实项中的偶必现难测bug--验证码问题
  • 【Qt】Macbook M1下载安装
  • 【juc】AbstractQueuedSynchronized为什么采用双向链表
  • 探索 JNI - Rust 与 Java 互调实战
  • Elasticsearch(ES)简介
  • 【MATLAB代码】二维平面上的TDOA,使用加权最小二乘法,不限制锚点数量,代码可复制粘贴
  • 16.useForm
  • (附源码)django仓库管理系统-计算机毕设 30542
  • Python数据分析中的Pandas去重操作详解
  • mysql备份数据库及恢复
  • Elasticsearch和Lucene之间是什么关系?(ChatGPT回答)
  • 小米面试:什么是线程池?工作原理是什么?线程池可以动态修改吗?
  • 【python】路径与文件管理:pathlib库的现代用法
  • 【WRF后处理】基于wrf-python处理wrf运行结果wrfout_d01
  • Linux:基本开发工具
  • 【go从零单排】Rate Limiting限流
  • 成都爱尔小儿眼科及视光团队多人当选“近视防控专家委员会委员”
  • CSS3_3D变换(七)
  • Vue CLI 脚手架
  • ubuntu 22.04 防火墙 ufw
  • imu_tk配置教程(锁死ubuntu18.04,不要22.04)
  • Spark的yarn集群环境搭建
  • C++ OpenCV 理想滤波
  • 挖掘web程序中的OAuth漏洞:利用redirect_uri和state参数接管账户
  • linux centos 安装redis
  • Qt_day4_Qt_UI设计