优先级队列(Priority Queue)

文章目录

  • 优先级队列(Priority Queue)
    • 实现方式
      • 基于数组实现
      • 基于堆实现
        • 方法实现
          • offer(E value)
          • poll()
          • peek()
          • isEmpty()
          • isFull()
    • 优先级队列的实现细节

优先级队列(Priority Queue)

优先级队列是一种特殊的队列,其中的元素不是按照进入队列的顺序出队,而是按照元素的优先级出队。在优先级队列中,元素的优先级最高的将会首先出队。

实现方式

基于数组实现

以下是基于数组的优先级队列的简单实现:

public class PriorityQueueArray<E extends Priority> {
    private E[] array;
    private int size = 0;

    public PriorityQueueArray(int capacity) {
        array = (E[]) new Object[capacity];
    }

    public boolean offer(E value) {
        if (size >= array.length) return false;
        int i = size - 1;
        while (i >= 0 && array[i].priority < value.priority) {
            array[i + 1] = array[i];
            i--;
        }
        array[i + 1] = value;
        size++;
        return true;
    }

    public E poll() {
        if (size == 0) return null;
        E result = array[size - 1];
        array[size - 1] = null;
        size--;
        return result;
    }

    public E peek() {
        if (size == 0) return null;
        return array[size - 1];
    }

    public boolean isEmpty() {
        return size == 0;
    }

    public boolean isFull() {
        return size == array.length;
    }
}

这个实现中,offer方法将元素插入到正确的位置以保持数组的有序性,poll方法删除并返回优先级最高的元素,peek方法返回但不删除优先级最高的元素。isEmptyisFull方法分别用于检查队列是否为空或已满。

基于堆实现

基于数组的实现有一些缺点。例如,插入和删除元素可能需要移动大量的元素,特别是在最坏的情况下,这可能需要移动整个数组。因此,这种实现的时间复杂度可能会达到O(n),其中n是队列的大小。

这就是为什么在实践中,我们通常会使用更复杂的数据结构,如堆,来实现优先级队列。使用堆实现的优先级队列可以在O(log n)的时间复杂度内插入和删除元素,这比基于数组的实现更有效率。

请添加图片描述

优先级队列通常使用堆(Heap)数据结构来实现。在Java中,可以通过实现Queue接口来创建一个优先级队列。下面的代码是一个使用最大堆实现的优先级队列:

public class PriorityQueue2<E extends Priority> implements Queue<E> {
    Priority[] array;
    public int size;

    public PriorityQueue2(int capacity) {
        array = new Priority[capacity];
    }
    ...
}

这个优先级队列中的元素必须实现Priority接口,这个接口定义了元素的优先级。

方法实现

优先级队列通常包含以下方法:

offer(E value)

将元素插入到优先级队列中。如果队列已满,返回false;否则,将元素插入到正确的位置以保持堆的性质,并返回true

@Override
public boolean offer(E value) {
    if(isFull())
        return false;
    if (size == 0){
        array[0] = value;
    }
    else{
        int child = size;
        int partent = (child - 1) / 2;
        while (child > 0 && value.priority > array[partent].priority){
            array[child] = array[partent];
            child =  partent;
            partent = (child - 1) / 2;
        }
        array[child] = value;
    }
    size++;
    return true;
};
poll()

移除并返回优先级最高的元素。如果队列为空,返回null

@Override
public E poll() {
    if (isEmpty())
        return null;
    E result = (E)array[0];
    array[0] = array[size-1];
    array[size] = null;
    size--;
    down(0);

    return result;
}

private void down(int parent){
    int child1 = parent * 2 + 1;
    int child2 = parent * 2 + 2;

    if(child1 >= size )
        return;
    int maxIndex = child2 < size &&  array[child2].priority > array[child1].priority 
        ? child2: child1;
    if(array[maxIndex].priority <= array[parent].priority)
        return;
    change(parent,maxIndex);
    down(maxIndex);
}

private void change(int parent,int child){
    Priority p = array[parent];
    array[parent] = array[child];
    array[child] = p;
}
peek()

返回优先级最高的元素,但不移除它。如果队列为空,返回null

@Override
public E peek() {
    if (isEmpty())
        return null;
    return (E)array[0];
}
isEmpty()

判断队列是否为空。

@Override
public boolean isEmpty() {
    return size == 0;
}
isFull()

判断队列是否已满。

@Override
public boolean isFull() {
    return size == array.length;
}

优先级队列的实现细节

优先级队列的实现主要基于一个堆结构。堆是一种特殊的完全二叉树,其中每个节点的值都大于或等于其子节点的值(最大堆)或小于或等于其子节点的值(最小堆)。

在我们的实现中,我们使用了一个数组array来存储堆的元素,并使用size来记录堆的大小。这是因为完全二叉树可以非常方便地用数组来表示。具体来说,对于数组中的任何一个元素,其左子节点的索引是2 * index + 1,右子节点的索引是2 * index + 2,而其父节点的索引是(index - 1) / 2

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

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

Jsqlparser简单学习

文章目录 学习链接模块访问者模式parser模块statement模块Expression模块deparser模块 测试TestDropTestSelectTestSelectVisitor 学习链接 java设计模式&#xff1a;访问者模式 github使用示例参考 测试 JSqlParser使用示例 JSqlParse&#xff08;一&#xff09;基本增删改…

第02章_变量与运算符拓展练习

文章目录 第02章_变量与运算符拓展练习1、辨别标识符2、数据类型转换简答3、判断如下代码的运行结果(难)4、判断如下程序的运行结果5、判断如下程序的运行结果6、Java的基本数据类型有哪些&#xff1f;String是基本数据类型吗&#xff1f;7、语法判断8、char型变量中是否可以存…

LeeCode前端算法基础100题(20)找出字符串中第一个匹配项的下标

一、问题详情: 给你两个字符串 haystack 和 needle ,请你在 haystack 字符串中找出 needle 字符串的第一个匹配项的下标(下标从 0 开始)。如果 needle 不是 haystack 的一部分,则返回 -1 。 示例 1: 输入:haystack = "sadbutsad", needle = "s…

【现代密码学】笔记 补充7-- CCA安全与认证加密《introduction to modern cryphtography》

【现代密码学】笔记7-- CCA安全与认证加密《introduction to modern cryphtography》 写在最前面7 CCA安全与认证加密 写在最前面 主要在 哈工大密码学课程 张宇老师课件 的基础上学习记录笔记。 内容补充&#xff1a;骆婷老师的PPT 《introduction to modern cryphtography》…

鸿蒙应用开发学习:让page页面强制横屏

一、学习做了个适合横屏的页面但进入页面后是竖屏显示的 前几天在B站上跟着 黑马程序员的 HarmonyOS4.0开发应用教学视频学习了显式动画&#xff08;animateTo&#xff09;和属性动画&#xff08;animation&#xff09;功能&#xff0c;并参照教学视频的内容做了个小鱼动画。…

助力工业园区作业违规行为检测预警,基于YOLOv7【tiny/l/x】不同系列参数模型开发构建工业园区场景下作业人员违规行为检测识别系统

在很多工业园区生产作业场景下保障合规合法进行作业生产操作&#xff0c;对于保护工人生命安全降低安全隐患有着非常重要的作用&#xff0c;但是往往在实际的作业生产中&#xff0c;因为一个安全观念的淡薄或者是粗心大意&#xff0c;对于纪律约束等意思薄弱&#xff0c;导致在…

绝地求生:【PC】第27赛季第2轮更新公告

各位玩家大家好&#xff01;欢迎收看本期闲游盒更新公告。 正式服维护时间 ※ 下列时间可能会根据维护情况而发生变化。 1月10日上午8:00 – 下午4:30 地图轮换 ※ 地图轮换将于每周三上午10点进行。 ※ 在随机选择地图的地区中&#xff0c;第1周可选择荣都地图&#xff0c…

UML-通信图和交互概览图(通信图和顺序图的区别与联系)

UML-通信图和交互概览图&#xff08;通信图和顺序图的区别与联系&#xff09; 一、通信图简介1.消息2.链接 二、通信图和[顺序图](https://blog.csdn.net/weixin_65032328/article/details/135587782)的联系与区别三、交互概览图四、顺序图转化为通信图练习 一、通信图简介 通…

CSC8021_computer network_The Transport Layer

Role of the transport layer • The transport layer is responsible for providing a reliable end-to-end connection between two application processes in a network • Abstracting away the physical subnet • Does not involve intermediate nodes • Takes a netwo…

2024--Django平台开发-Redis集群(十一)

内容回顾 主从复制。 哨兵&#xff1a;实例启动了&#xff0c;哨兵节点没启动&#xff0c;Python通过redis-py连接报错。一定要确保实例节点和哨兵节点都启动了。 搭建集群用的是虚拟机的多台centos服务器&#xff0c;你在跟着学习的时候&#xff0c;一定要全部都是虚拟机&am…

MySQL面试题2

文章目录 面试题 (9-15) 面试题 (9-15) 09&#xff09;查询学过「张三」老师授课的同学的信息 SELECT s.*,c.cname,t.tname FROM t_mysql_teacher t,t_mysql_student s,t_mysql_course c,t_mysql_score sc WHERE t.tidc.tid and c.cidsc.cid and sc.sids.sid and tname ‘张…

EI级 | Matlab实现VMD-TCN-BiLSTM变分模态分解结合时间卷积双向长短期记忆神经网络多变量光伏功率时间序列预测

EI级 | Matlab实现VMD-TCN-BiLSTM变分模态分解结合时间卷积双向长短期记忆神经网络多变量光伏功率时间序列预测 目录 EI级 | Matlab实现VMD-TCN-BiLSTM变分模态分解结合时间卷积双向长短期记忆神经网络多变量光伏功率时间序列预测预测效果基本介绍程序设计参考资料 预测效果 基…

QLExpress和Groovy对比

原理 Groovy groovy基于JVM运行。 编译时&#xff1a;将源文件编译成class文件后&#xff0c;用java的classLoader加载&#xff1b;运行时&#xff1a;直接用groovy classLoader加载 QLExpress QLExpress将文本解析成AST&#xff0c;用java对象表达后执行。 特点 Groo…

如何用LLM和自有知识库搭建智能agent?

用LangChain建立知识库&#xff0c;文末中也推荐其他方案。 项目源码&#xff1a;ChatPDF实现 LangChain Indexes使用 对加载的内容进行索引&#xff0c;在indexes中提供了一些功能&#xff1a; Document Loaders&#xff0c;加载文档Text Splitters&#xff0c;文档切分V…

android.os.NetworkOnMainThreadException

问题 android.os.NetworkOnMainThreadException详细问题 核心代码如下&#xff1a; import android.os.Bundle;import androidx.appcompat.app.AppCompatActivity;import java.io.BufferedReader; import java.io.IOException; import java.io.InputStreamReader; import ja…

【Java】IDEA中的JFormDesigner使用教程

目录 1 安装 JFormDesigner 插件2 JFormDesigner 使用教程2.1 新建JFormDesigner Form时的选项2.2 JFormDesigner Form界面布局2.3 JFormDesigner 常用组件 JFormDesigner 是一款用于设计和创建图形用户界面&#xff08;GUI&#xff09;的插件&#xff0c;它允许开发者使用可视…

鸿蒙Harmony-相对布局(RelativeContainer)详解

成年人的世界&#xff0c;从来没有容易二字&#xff0c;想要什么&#xff0c;就得凭自己的努力去拿&#xff0c;遇到事情就得自己生生的硬抗&#xff0c;希望你即使再辛苦&#xff0c;但还是会选择这滚烫的人生&#xff0c;加油陌生的朋友们 目录 一&#xff0c;定义 二&#x…

瑞_Java开发手册_(一)编程规约

文章目录 编程规约的意义&#xff08;一&#xff09;命名风格&#xff08;二&#xff09;常量定义&#xff08;三&#xff09;代码格式&#xff08;四&#xff09;OOP 规约&#xff08;五&#xff09;日期时间&#xff08;六&#xff09;集合处理&#xff08;七&#xff09;并发…

网络分流规则

现在的网络是越来越复杂。 有必要进行分流。 有一些geosite.dat是已经整理好的&#xff0c;包含许多的网站的分类&#xff1a; 分流规则&#xff1a; route规则 主要是: {"type": "field","outboundTag": "direct","domain&quo…

Material Design 进阶(十一)——Chip,ChipGroup,ChipDrawable使用

流式布局标签发展历程 第一阶段&#xff1a;实现这种界面的时候&#xff0c;基本都是自定义一个控件&#xff0c;然后在Java代码中动态的 添加一个个的TextView&#xff0c;还需要计算布局宽度/高度&#xff0c;进行换行等等处理&#xff0c;比较复杂;第二阶段&#xff1a;使用…