优先级队列

一、PriorityQueue

PriorityQueue是优先级队列,它实现了Queue接口,它的队列长度

没有限制,与一般队列的区别是,它有优先级概念,每个元素都有优先

级,队头的元素永远都是优先级最高的。PriorityQueue内部是用堆实现的。

一、基本用法

主要构造方法:

public PriorityQueue()
public PriorityQueue(int initialCapacity, Comparator<? super E> comparator)
public PriorityQueue(Collection<? extends E> c) //动态数组大小等于容器中元素的个数

PriorityQueue使用动态数组initialCapacity表示初始数组的大小。举例:

PriorityQueue<Integer> ints = new PriorityQueue<>();
ints.offer(10);
ints.add(28);
ints.addAll(Arrays.asList(22, 33, 55, 66));
while (ints.peek() != null) {
System.out.println(ints.poll() + " ");
}

二、实现原理

内部成员:

private transient Object[] queue;
private int size = 0;
private final Comparator<? super E> comparator;
private transient int modCount = 0;

构造方法:

public PriorityQueue() {
this(DEFAULT_INITIAL_CAPACITY, null);
}
public PriorityQueue(int initialCapacity) {
this(initialCapacity, null);
}
public PriorityQueue(int initialCapacity,
Comparator<? super E> comparator) {
if(initialCapacity < 1)
throw new IllegalArgumentException();
this.queue = new Object[initialCapacity];
this.comparator = comparator;
}

添加元素的代码

public boolean offer(E e) {
if(e == null)
throw new NullPointerException();
modCount++;
int i = size;
if(i >= queue.length) //先确保数组长度是否足够,如果不够,用grow方法扩展઀
grow(i + 1);
size = i + 1;
if(i == 0) //如果是第一次添加
queue[0] = e;
else //否则将其放入最后一个位置,并向上调整
siftUp(i, e);return true;
}
private void grow(int minCapacity) {
int oldCapacity = queue.length;
// Double size if small; else grow by 50%
int newCapacity = oldCapacity + ((oldCapacity < 64)
(oldCapacity + 2) :
(oldCapacity >> 1));
// overflow-conscious code
if(newCapacity - MAX_ARRAY_SIZE > 0)
newCapacity = hugeCapacity(minCapacity);
queue = Arrays.copyOf(queue, newCapacity);
}
private void siftUp(int k, E x) {
if(comparator != null)
siftUpUsingComparator(k, x);
else
siftUpComparable(k, x);
}
private void siftUpUsingComparator(int k, E x) {
while(k > 0) {
int parent = (k - 1) >>> 1;
Object e = queue[parent];
if(comparator.compare(x, (E) e) >= 0)
break;
queue[k] = e;
k = parent;
}
queue[k] = x;
}

查看元素头部元素:

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

删除头部元素:略

三、总结

1)实现了优先级队列,最先出队的总是优先级最高的,即排序中的第一个。

2)优先级可以有相同的,内部元素不是完全有序的,如果遍历输出,除了第一个其他没有特定顺序。、

3)查看头部元素,入队出队的效率都很高

4)根据值查找和删除元素的效率很低。

Java笔记(十)堆与优先级队列的更多相关文章

  1. 自己动手实现java数据结构(八) 优先级队列

    1.优先级队列介绍 1.1 优先级队列 有时在调度任务时,我们会想要先处理优先级更高的任务.例如,对于同一个柜台,在决定队列中下一个服务的用户时,总是倾向于优先服务VIP用户,而让普通用户等待,即使普 ...

  2. 笔试算法题(57):基于堆的优先级队列实现和性能分析(Priority Queue based on Heap)

    议题:基于堆的优先级队列(最大堆实现) 分析: 堆有序(Heap-Ordered):每个节点的键值大于等于该节点的所有孩子节点中的键值(如果有的话),而堆数据结构的所有节点都按照完全有序二叉树 排.当 ...

  3. Java集合总结(三):堆与优先级队列

    堆 满二叉树:满二叉树是指,除了最后一层外,每个节点都有两个孩子,而最后一层都是叶子节点,都没有孩子. 完全二叉树:完全二叉树不要求最后一层是满的,但如果不满,则要求所有节点必须集中在最左边,从左到右 ...

  4. 【数据结构与算法Python版学习笔记】树——利用二叉堆实现优先级队列

    概念 队列有一个重要的变体,叫作优先级队列. 和队列一样,优先级队列从头部移除元素,不过元素的逻辑顺序是由优先级决定的. 优先级最高的元素在最前,优先级最低的元素在最后. 实现优先级队列的经典方法是使 ...

  5. java数据结构与算法值优先级队列

    一.优先级队列 什么是优先级队列:优先级队列是一种比栈和队列更加常用的一种数据结构.在优先级队列中,数据项按照关键字的值有序.数据项插入到队列中时,会按照顺序插入到合适的位置,用来保证队列的顺序. 生 ...

  6. Java笔记(十二)……类中各部分加载顺序及存放位置问题

    什么时候会加载类 使用到类中的内容时加载,三种情况: 创建对象:new StaticDemo(); 使用类中的静态成员:StaticCode.num = 9;  StaticCode.getNum() ...

  7. SpringBoot笔记十四:消息队列

    目录 什么是消息队列 消息队列的作用 异步通信 应用解耦 流量削峰 RabbitMQ RabbitMQ流程简介 RabbitMQ的三种模式 安装RabbitMQ RabbitMQ交换器路由和队列的创建 ...

  8. Java笔记(十九)……多线程

    概述 进程: 是一个正在执行中的程序 每一个进程执行都有一个执行顺序,该执行顺序是一个执行路径,或者叫一个控制单元 线程: 就是进程中的一个独立的控制单元,线程在控制着进程的执行 一个进程中至少有一个 ...

  9. Java笔记(十八)……包

    概述 对类文件进行分类管理. 给类提供多层命名空间. 写在程序文件的第一行. 类名的全称的是 包名.类名. 包也是一种封装形式. 访问权限 引用<The Complete Reference&g ...

随机推荐

  1. cf861D 字典树+时间戳

    好久没碰字典树之类的题了,搞起来有点生疏 /* 把所有母串的后缀加入字典树中 然后再扫一次所有母串的后缀,把后缀放到字典树中查询,找到第一个访问次数为1的结点返回即可 num在计数时,同一个母串的子串 ...

  2. 用HBuilderX 打包 vue 项目 为 App 的步骤

    首先打包你的 vue 项目 生成 dist 文件夹,教程请移步  https://www.cnblogs.com/taohuaya/p/10256670.html 看完上面的教程,请确保 你是 将: ...

  3. VMware 虚拟机 Ubuntu 系统执行 ifconfig 命令 eth0没有IP地址(intet addr、Bcast、Mask) 解决:UP BROADCAST MULTICAST 问题

    VMware 虚拟机 ifconfig没有net_addr地址.Bcast.Mask的解决方法 使用时间长的虚拟机,会莫名其妙的连接不上网 在终端中,使用ifconfig命令查看Ubuntu系统的IP ...

  4. 史上最简单的SpringCloud教程 | 第九篇: 服务链路追踪(Spring Cloud Sleuth)

    这篇文章主要讲述服务追踪组件zipkin,Spring Cloud Sleuth集成了zipkin组件. 注意情况: 该案例使用的spring-boot版本1.5.x,没使用2.0.x, 另外本文图3 ...

  5. 剑指offer错题记录

    错误重点: 1. 传递vector参数时,如果调用函数改变了vector的内容,一定一定要&,传引用保持一致 旋转数组的最小数字:有重复数字情况,二分查找照样搞.情况考虑要周全,当a[mid] ...

  6. 线程 ID

    摘自<Linux 环境编程:从应用到内核> 在 Linux 中,目前的线程实现是 Native POSIX Thread Library,简称 NPTL.在这种实现下,线程又被称为轻量级进 ...

  7. SPOJ 1812 LCS2

    题解: 和上一题差不多 每个点记录前面的到这个点的最大值 初值赋为len[i] 然后注意要用子节点更新父节点 代码: #include <bits/stdc++.h> #define ll ...

  8. vscode git

    Git 全局设置: git config --global user.name "xxxx" git config --global user.email "123456 ...

  9. MySQL 命令总结

    MySQL命令总结 1.数据库操作 查看在当前服务器中有多少个数据库 创建数据库 >CREATE DATABASE db_name DEFAULT CHARACTER SET utf8 COLL ...

  10. Codeforces 311D Interval Cubing 数学 + 线段树 (看题解)

    Interval Cubing 这种数学题谁顶得住啊. 因为 (3 ^ 48) % (mod - 1)为 1 , 所以48个一个循环节, 用线段树直接维护. #include<bits/stdc ...