借助heap数据结构实现。

以小顶heap为例(说明值越小优先级越高,如距离),代码如下:

 //  PriorityQueue.java
// Java Spatial Index Library
// Copyright (C) 2008 aled@users.sourceforge.net
//
// This library is free software; you can redistribute it and/or
// modify it under the terms of the GNU Lesser General Public
// License as published by the Free Software Foundation; either
// version 2.1 of the License, or (at your option) any later version.
//
// This library is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
// Lesser General Public License for more details.
//
// You should have received a copy of the GNU Lesser General Public
// License along with this library; if not, write to the Free Software
// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA package buaa.act.ucar.moi; import java.io.Serializable; import gnu.trove.list.array.TFloatArrayList;
import gnu.trove.list.array.TIntArrayList; /**
* <p>
* Priority Queue that stores values as ints and priorities as floats. Uses a
* Heap to sort the priorities; the values are sorted "in step" with the
* priorities.
* </p>
* <p>
* A Heap is simply an array that is kept semi sorted; in particular if the
* elements of the array are arranged in a tree structure; ie
* </p>
*
* <pre>
* 00
* / \
* 01 02
* / \ / \
* 03 04 05 06
* /\ /\ /\ /\
* 07 08 09 10 11 12 13 14
* </pre>
* <p>
* then each parent is kept sorted with respect to it's immediate children. E.g.
* 00 < 01, 00 < 02, 02 < 05, 02 < 06
* </p>
* <p>
* This means that the array appears to be sorted, as long as we only ever look
* at element 0.
* </p>
* <p>
* Inserting new elements is much faster than if the entire array was kept
* sorted; a new element is appended to the array, and then recursively swapped
* with each parent to maintain the "parent is sorted w.r.t it's children"
* property.
* </p>
* <p>
* To return the "next" value it is necessary to remove the root element. The
* last element in the array is placed in the root of the tree, and is
* recursively swapped with one of it's children until the "parent is sorted
* w.r.t it's children" property is restored.
* </p>
* <p>
* Random access is slow (eg for deleting a particular value), and is not
* implemented here - if this functionality is required, then a heap probably
* isn't the right data structure.
* </p>
*/
public class PriorityQueue implements Serializable {
private static final long serialVersionUID = -5653506138757217673L;
public static final boolean SORT_ORDER_ASCENDING = true;
public static final boolean SORT_ORDER_DESCENDING = false; private TIntArrayList values = null;
private TFloatArrayList priorities = null;
private boolean sortOrder = SORT_ORDER_ASCENDING; private static boolean INTERNAL_CONSISTENCY_CHECKING = false; public PriorityQueue(boolean sortOrder) {
this(sortOrder, 10);
} public PriorityQueue(boolean sortOrder, int initialCapacity) {
this.sortOrder = sortOrder;
values = new TIntArrayList(initialCapacity);
priorities = new TFloatArrayList(initialCapacity);
} /**
* @param p1
* @param p2
* @return true if p1 has an earlier sort order than p2.
*/
private boolean sortsEarlierThan(float p1, float p2) {
if (sortOrder == SORT_ORDER_ASCENDING) {
return p1 < p2;
}
return p2 < p1;
} // to insert a value, append it to the arrays, then
// reheapify by promoting it to the correct place.
public void insert(int value, float priority) {
values.add(value);
priorities.add(priority); promote(values.size() - 1, value, priority);
} private void promote(int index, int value, float priority) {
// Consider the index to be a "hole"; i.e. don't swap priorities/values
// when moving up the tree, simply copy the parent into the hole and
// then consider the parent to be the hole.
// Finally, copy the value/priority into the hole.
while (index > 0) {
int parentIndex = (index - 1) / 2;
float parentPriority = priorities.get(parentIndex); if (sortsEarlierThan(parentPriority, priority)) {
break;
} // copy the parent entry into the current index.
values.set(index, values.get(parentIndex));
priorities.set(index, parentPriority);
index = parentIndex;
} values.set(index, value);
priorities.set(index, priority); if (INTERNAL_CONSISTENCY_CHECKING) {
check();
}
} public int size() {
return values.size();
} public void clear() {
values.clear();
priorities.clear();
} public void reset() {
values.reset();
priorities.reset();
} public int getValue() {
return values.get(0);
} public float getPriority() {
return priorities.get(0);
} private void demote(int index, int value, float priority) {
int childIndex = (index * 2) + 1; // left child while (childIndex < values.size()) {
float childPriority = priorities.get(childIndex); if (childIndex + 1 < values.size()) {
float rightPriority = priorities.get(childIndex + 1);
if (sortsEarlierThan(rightPriority, childPriority)) {
childPriority = rightPriority;
childIndex++; // right child
}
} if (sortsEarlierThan(childPriority, priority)) {
priorities.set(index, childPriority);
values.set(index, values.get(childIndex));
index = childIndex;
childIndex = (index * 2) + 1;
} else {
break;
}
} values.set(index, value);
priorities.set(index, priority);
} // get the value with the lowest priority
// creates a "hole" at the root of the tree.
// The algorithm swaps the hole with the appropriate child, until
// the last entry will fit correctly into the hole (ie is lower
// priority than its children)
public int pop() {
int ret = values.get(0); // record the value/priority of the last entry
int lastIndex = values.size() - 1;
int tempValue = values.get(lastIndex);
float tempPriority = priorities.get(lastIndex); values.removeAt(lastIndex);
priorities.removeAt(lastIndex); if (lastIndex > 0) {
demote(0, tempValue, tempPriority);
} if (INTERNAL_CONSISTENCY_CHECKING) {
check();
} return ret;
} public void setSortOrder(boolean sortOrder) {
if (this.sortOrder != sortOrder) {
this.sortOrder = sortOrder;
// reheapify the arrays
for (int i = (values.size() / 2) - 1; i >= 0; i--) {
demote(i, values.get(i), priorities.get(i));
}
}
if (INTERNAL_CONSISTENCY_CHECKING) {
check();
}
} private void check() {
// for each entry, check that the child entries have a lower or equal
// priority
int lastIndex = values.size() - 1; for (int i = 0; i < values.size() / 2; i++) {
float currentPriority = priorities.get(i); int leftIndex = (i * 2) + 1;
if (leftIndex <= lastIndex) {
float leftPriority = priorities.get(leftIndex);
if (sortsEarlierThan(leftPriority, currentPriority)) {
System.err.println("Internal error in PriorityQueue");
}
} int rightIndex = (i * 2) + 2;
if (rightIndex <= lastIndex) {
float rightPriority = priorities.get(rightIndex);
if (sortsEarlierThan(rightPriority, currentPriority)) {
System.err.println("Internal error in PriorityQueue");
}
}
}
}
}

PriorityQueue的Java实现的更多相关文章

  1. Java中的队列Queue,优先级队列PriorityQueue

    队列Queue 在java5中新增加了java.util.Queue接口,用以支持队列的常见操作.该接口扩展了java.util.Collection接口. Queue使用时要尽量避免Collecti ...

  2. java中PriorityQueue优先级队列使用方法

    优先级队列是不同于先进先出队列的另一种队列.每次从队列中取出的是具有最高优先权的元素. PriorityQueue是从JDK1.5开始提供的新的数据结构接口. 如果不提供Comparator的话,优先 ...

  3. 《转》JAVA中PriorityQueue优先级队列使用方法

    该文章转自:http://blog.csdn.net/hiphopmattshi/article/details/7334487 优先级队列是不同于先进先出队列的另一种队列.每次从队列中取出的是具有最 ...

  4. 【转】java中PriorityQueue优先级队列使用方法

    优先级队列是不同于先进先出队列的另一种队列.每次从队列中取出的是具有最高优先权的元素. PriorityQueue是从JDK1.5开始提供的新的数据结构接口. 如果不提供Comparator的话,优先 ...

  5. Java Queue之PriorityQueue

    PriorityQueue位于Java util包中,观其名字前半部分的单词Priority是优先的意思,实际上这个队列就是具有“优先级”.既然具有优先级的特性,那么就得有个前后排序的“规则”.所以其 ...

  6. # Java Queue系列之PriorityQueue

    在上一篇中我用一张图来梳理了一下Java中的各种Queue之间的关系.这里介绍下PriorityQueue.PriorityQueue位于Java util包中,观其名字前半部分的单词Priority ...

  7. java 中PriorityQueue优先级队列使用方法

    1.前言 优先级队列是不同于先进先出队列的另一种队列.每次从队列中取出的是具有最高优先权的元素. PriorityQueue是从JDK1.5开始提供的新的数据结构接口. 如果想实现按照自己的意愿进行优 ...

  8. 【Java源码】集合类-优先队列PriorityQueue

    一.类继承关系 public class PriorityQueue<E> extends AbstractQueue<E> implements java.io.Serial ...

  9. Java找N个数中最小的K个数,PriorityQueue和Arrays.sort()两种实现方法

    最近看到了 java.util.PriorityQueue.刚看到还没什么感觉,今天突然发现他可以用来找N个数中最小的K个数. 假设有如下 10 个整数. 5 2 0 1 4 8 6 9 7 3 怎么 ...

随机推荐

  1. [CTCI] 下一个较大元素

    下一个较大元素 题目描述 现在我们有一个int数组,请你找出数组中每个元素的下一个比它大的元素. 给定一个int数组A及数组的大小n,请返回一个int数组,代表每个元素比他大的下一个元素,若不存在则为 ...

  2. [sql]mysql指引(整理中...)-对db的分类

    参考 db存储及分层 一个db一个文件夹. 一张表两个文件frm是存表结构的,ibd是存数据的 连接层: sock ip sql层: 存储层: 2018年4月1日 20:53:54小结: 时间太久,抓 ...

  3. pc客户端网页录音和压缩

    web录音的功能,也就是怎么使用 getUserMedia 音频上传 栗子中最后返回的是Blob数据 return new Blob([dataview], { type: type }) 因为对ht ...

  4. 基于 Promise 的 HTTP 请求客户端 axios

    基于 Promise 的 HTTP 请求客户端,可同时在浏览器和 node.js 中使用 功能特性 在浏览器中发送 XMLHttpRequests 请求 在 node.js 中发送 http请求 支持 ...

  5. Multi-Cloud & Kubernetes: Cloud Academy November 2018 Data Report

    https://cloudacademy.com/research/multi-cloud-kubernetes-devops-cloud-academy-data-report-nov-18/ No ...

  6. [Windows Azure] Windows Azure Web Sites, Cloud Services, and VMs: When to use which?

    This document provides guidance on how to make an informed decision in choosing between Windows Azur ...

  7. iOS开发如何学习前端(2)

    iOS开发如何学习前端(2) 上一篇成果如下. 实现的效果如下. 实现了一个横放的<ul>,也既iOS中的UITableView. 实现了当鼠标移动到列表中的某一个<li>,也 ...

  8. Mac上把python源文件编译成so文件

    把python源文件编译成so文件 前言 实际上属于一种代码混淆/加密的技术,大家知道python的源文件放在那里,大家是都可以看的,不像C语言编译出来可以拿编译后的东西去运行,所以就出现了这种需求. ...

  9. C# LINQ系列:LINQ to DataSet的DataTable操作 及 DataTable与Linq相互转换

    LINQ to DataSet需要使用System.Core.dll.System.Data.dll和System.Data.DataSetExtensions.dll,在项目中添加引用System. ...

  10. VMware网络使用NAT模式

    公司的网络中,要在本地安装一个Linux虚拟机,但是只分配给宿主机一个IP,那么怎么实现Linux虚拟机的网络访问呢? 使用NAT模式:这是VMware用于虚拟NAT网络下的虚拟交换机. 1.设置网络 ...