PriorityQueue优先队列,即维持一个最大(最小)堆,使根节点最大(最小),其儿子节点都不大于(不小于)父节点。
简化的优先队列的变种在排序系列之堆排序和经典算法之最小生成树中使用。
class MiniPriorityQueue {
private final int queue[];
private int size;
public MiniPriorityQueue(int a[]) {
this.size = a.length;
this.queue = a;
heapify();
}
private void heapify() {
for (int i = (this.size >>> 1) - 1; i >= 0; i--)
siftDown(i, this.queue[i]);
}
private void siftDown(int index, int value) {
int i = this.size >>> 1;
while (index < i) {
int j = (index << 1) + 1;
int temp = this.queue[j];
int k = j + 1;
if ((k < this.size) && (this.queue[j] > this.queue[k])) {
temp = this.queue[(j = k)];
}
if (temp > value)
break;
this.queue[index] = temp;
index = j;
}
this.queue[index] = value;
}
public int pop(){
int result = this.queue[0];
int value = this.queue[--this.size];
siftDown(0, value);
return this.queue[this.size]=result;
}
public boolean isNotEmpty(){
return this.size != 0;
}
}
java API中完整版优先队列有兴趣的可以研究一下
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.io.Serializable;
import java.util.AbstractQueue;
import java.util.ArrayDeque;
import java.util.Arrays;
import java.util.Collection;
import java.util.Comparator;
import java.util.ConcurrentModificationException;
import java.util.Iterator;
import java.util.NoSuchElementException;
import java.util.SortedSet;
public class PriorityQueue<E> extends AbstractQueue<E>
implements Serializable
{
private static final long serialVersionUID = -7720805057305804111L;
private static final int DEFAULT_INITIAL_CAPACITY = 11;
private transient Object[] queue;
private int size = 0;
private final Comparator<? super E> comparator;
private transient int modCount = 0;
private static final int MAX_ARRAY_SIZE = 2147483639;
public PriorityQueue()
{
this(11, null);
}
public PriorityQueue(int paramInt)
{
this(paramInt, null);
}
public PriorityQueue(int paramInt, Comparator<? super E> paramComparator)
{
if (paramInt < 1)
throw new IllegalArgumentException();
this.queue = new Object[paramInt];
this.comparator = paramComparator;
}
public PriorityQueue(Collection<? extends E> paramCollection)
{
Object localObject;
if ((paramCollection instanceof SortedSet)) {
localObject = (SortedSet)paramCollection;
this.comparator = ((SortedSet)localObject).comparator();
initElementsFromCollection((Collection)localObject);
}
else if ((paramCollection instanceof PriorityQueue)) {
localObject = (PriorityQueue)paramCollection;
this.comparator = ((PriorityQueue)localObject).comparator();
initFromPriorityQueue((PriorityQueue)localObject);
}
else {
this.comparator = null;
initFromCollection(paramCollection);
}
}
public PriorityQueue(PriorityQueue<? extends E> paramPriorityQueue)
{
this.comparator = (Comparator<? super E>) paramPriorityQueue.comparator();
initFromPriorityQueue(paramPriorityQueue);
}
public PriorityQueue(SortedSet<? extends E> paramSortedSet)
{
this.comparator = (Comparator<? super E>) paramSortedSet.comparator();
initElementsFromCollection(paramSortedSet);
}
private void initFromPriorityQueue(PriorityQueue<? extends E> paramPriorityQueue) {
if (paramPriorityQueue.getClass() == PriorityQueue.class) {
this.queue = paramPriorityQueue.toArray();
this.size = paramPriorityQueue.size();
} else {
initFromCollection(paramPriorityQueue);
}
}
private void initElementsFromCollection(Collection<? extends E> paramCollection) {
Object[] arrayOfObject = paramCollection.toArray();
int i = arrayOfObject.length;
if ((i == 1) || (this.comparator != null))
for (int j = 0; j < i; j++)
if (arrayOfObject[j] == null)
throw new NullPointerException();
this.queue = arrayOfObject;
this.size = arrayOfObject.length;
}
private void initFromCollection(Collection<? extends E> paramCollection)
{
initElementsFromCollection(paramCollection);
heapify();
}
private void grow(int paramInt)
{
int i = this.queue.length;
int j = i + (i < 64 ? i + 2 : i >> 1);
if (j - 2147483639 > 0)
j = hugeCapacity(paramInt);
this.queue = Arrays.copyOf(this.queue, j);
}
private static int hugeCapacity(int paramInt) {
if (paramInt < 0)
throw new OutOfMemoryError();
return paramInt > 2147483639 ? 2147483647 : 2147483639;
}
public boolean add(E paramE)
{
return offer(paramE);
}
public boolean offer(E paramE)
{
if (paramE == null)
throw new NullPointerException();
this.modCount += 1;
int i = this.size;
if (i >= this.queue.length)
grow(i + 1);
this.size = (i + 1);
if (i == 0)
this.queue[0] = paramE;
else
siftUp(i, paramE);
return true;
}
public E peek() {
if (this.size == 0)
return null;
return (E)this.queue[0];
}
private int indexOf(Object paramObject) {
if (paramObject != null) {
for (int i = 0; i < this.size; i++)
if (paramObject.equals(this.queue[i]))
return i;
}
return -1;
}
public boolean remove(Object paramObject)
{
int i = indexOf(paramObject);
if (i == -1) {
return false;
}
removeAt(i);
return true;
}
boolean removeEq(Object paramObject)
{
for (int i = 0; i < this.size; i++) {
if (paramObject == this.queue[i]) {
removeAt(i);
return true;
}
}
return false;
}
public boolean contains(Object paramObject)
{
return indexOf(paramObject) != -1;
}
public Object[] toArray()
{
return Arrays.copyOf(this.queue, this.size);
}
public <T> T[] toArray(T[] paramArrayOfT)
{
if (paramArrayOfT.length < this.size)
{
return (T[])Arrays.copyOf(this.queue, this.size, paramArrayOfT.getClass());
}
System.arraycopy(this.queue, 0, paramArrayOfT, 0, this.size);
if (paramArrayOfT.length > this.size)
paramArrayOfT[this.size] = null;
return paramArrayOfT;
}
public Iterator<E> iterator()
{
return new Itr();
}
public int size()
{
return this.size;
}
public void clear()
{
this.modCount += 1;
for (int i = 0; i < this.size; i++)
this.queue[i] = null;
this.size = 0;
}
public E poll() {
if (this.size == 0)
return null;
int i = --this.size;
this.modCount += 1;
E localObject1 = (E)this.queue[0];
E localObject2 = (E)this.queue[i];
this.queue[i] = null;
if (i != 0)
siftDown(0, localObject2);
return localObject1;
}
private E removeAt(int paramInt)
{
assert ((paramInt >= 0) && (paramInt < this.size));
this.modCount += 1;
int i = --this.size;
if (i == paramInt) {
this.queue[paramInt] = null;
} else {
E localObject = (E)this.queue[i];
this.queue[i] = null;
siftDown(paramInt, localObject);
if (this.queue[paramInt] == localObject) {
siftUp(paramInt, localObject);
if (this.queue[paramInt] != localObject)
return localObject;
}
}
return null;
}
private void siftUp(int paramInt, E paramE)
{
if (this.comparator != null)
siftUpUsingComparator(paramInt, paramE);
else
siftUpComparable(paramInt, paramE);
}
private void siftUpComparable(int paramInt, E paramE) {
Comparable localComparable = (Comparable)paramE;
while (paramInt > 0) {
int i = paramInt - 1 >>> 1;
Object localObject = this.queue[i];
if (localComparable.compareTo(localObject) >= 0)
break;
this.queue[paramInt] = localObject;
paramInt = i;
}
this.queue[paramInt] = localComparable;
}
private void siftUpUsingComparator(int paramInt, E paramE) {
while (paramInt > 0) {
int i = paramInt - 1 >>> 1;
E localObject = (E)this.queue[i];
if (this.comparator.compare(paramE, localObject) >= 0)
break;
this.queue[paramInt] = localObject;
paramInt = i;
}
this.queue[paramInt] = paramE;
}
private void siftDown(int paramInt, E paramE)
{
if (this.comparator != null)
siftDownUsingComparator(paramInt, paramE);
else
siftDownComparable(paramInt, paramE);
}
private void siftDownComparable(int paramInt, E paramE) {
Comparable localComparable = (Comparable)paramE;
int i = this.size >>> 1;
while (paramInt < i) {
int j = (paramInt << 1) + 1;
Object localObject = this.queue[j];
int k = j + 1;
if ((k < this.size) && (((Comparable)localObject).compareTo(this.queue[k]) > 0))
{
localObject = this.queue[(j = k)];
}if (localComparable.compareTo(localObject) <= 0)
break;
this.queue[paramInt] = localObject;
paramInt = j;
}
this.queue[paramInt] = localComparable;
}
private void siftDownUsingComparator(int paramInt, E paramE) {
int i = this.size >>> 1;
while (paramInt < i) {
int j = (paramInt << 1) + 1;
E localObject = (E)this.queue[j];
int k = j + 1;
if ((k < this.size) && (this.comparator.compare(localObject, (E)this.queue[k]) > 0))
{
localObject = (E)this.queue[(j = k)];
}if (this.comparator.compare(paramE, localObject) <= 0)
break;
this.queue[paramInt] = localObject;
paramInt = j;
}
this.queue[paramInt] = paramE;
}
private void heapify()
{
for (int i = (this.size >>> 1) - 1; i >= 0; i--)
siftDown(i, (E)this.queue[i]);
}
public Comparator<? super E> comparator()
{
return this.comparator;
}
private void writeObject(ObjectOutputStream paramObjectOutputStream)
throws IOException
{
paramObjectOutputStream.defaultWriteObject();
paramObjectOutputStream.writeInt(Math.max(2, this.size + 1));
for (int i = 0; i < this.size; i++)
paramObjectOutputStream.writeObject(this.queue[i]);
}
private void readObject(ObjectInputStream paramObjectInputStream)
throws IOException, ClassNotFoundException
{
paramObjectInputStream.defaultReadObject();
paramObjectInputStream.readInt();
this.queue = new Object[this.size];
for (int i = 0; i < this.size; i++) {
this.queue[i] = paramObjectInputStream.readObject();
}
heapify();
}
private final class Itr
implements Iterator<E>
{
private int cursor = 0;
private int lastRet = -1;
private ArrayDeque<E> forgetMeNot = null;
private E lastRetElt = null;
private int expectedModCount = PriorityQueue.this.modCount;
private Itr() { }
public boolean hasNext() { return (this.cursor < PriorityQueue.this.size) || ((this.forgetMeNot != null) && (!this.forgetMeNot.isEmpty()));
}
public E next()
{
if (this.expectedModCount != PriorityQueue.this.modCount)
throw new ConcurrentModificationException();
if (this.cursor < PriorityQueue.this.size)
return (E)PriorityQueue.this.queue[(this.lastRet = this.cursor++)];
if (this.forgetMeNot != null) {
this.lastRet = -1;
this.lastRetElt = this.forgetMeNot.poll();
if (this.lastRetElt != null)
return this.lastRetElt;
}
throw new NoSuchElementException();
}
public void remove() {
if (this.expectedModCount != PriorityQueue.this.modCount)
throw new ConcurrentModificationException();
if (this.lastRet != -1) {
E localObject = (E)PriorityQueue.this.removeAt(this.lastRet);
this.lastRet = -1;
if (localObject == null) {
this.cursor -= 1;
} else {
if (this.forgetMeNot == null)
this.forgetMeNot = new ArrayDeque();
this.forgetMeNot.add(localObject);
}
} else if (this.lastRetElt != null) {
PriorityQueue.this.removeEq(this.lastRetElt);
this.lastRetElt = null;
} else {
throw new IllegalStateException();
}
this.expectedModCount = PriorityQueue.this.modCount;
}
}
public static void main(String[] args) {
PriorityQueue<Integer> queue = new PriorityQueue<>();
for(int i=0;i<10;i++){
int result = (int)(Math.random()*100);
System.out.println(queue + " "+ result);
queue.add(result);
System.out.println(queue);
}
for(int i=0;i<10;i++){
System.out.println(queue.poll());
System.out.println(queue);
}
}
}