单向队列和优先级队列

来源:互联网 发布:json在qt中的使用 编辑:程序博客网 时间:2024/06/05 03:49

一、队列的概念

队列(queue)是一种特殊的线性表,特殊之处在于它只允许在表的前端(front)进行删除操作,而在表的后端(rear)进行插入操作,和栈一样,队列是一种操作受限制的线性表。进行插入操作的端称为队尾,进行删除操作的端称为队头。队列中没有元素时,称为空队列。

队列的数据元素又称为队列元素。在队列中插入一个队列元素称为入队,从队列中删除一个队列元素称为出队。因为队列只允许在一端插入,在另一端删除,所以只有最早进入队列的元素才能最先从队列中删除,故队列又称为先进先出(FIFO—first in first out)线性表。

在比如在计算机操作系统中,有各种队列在安静的工作着,比如打印机在打印列队中等待打印。

队列和栈是相反的,栈是后进先出,队列是先进先出。

二、单向队列

队列的实现原理如下:

1,队列中的数据不总是从数组的0下标开始的,移除一些队头front的数据后,队头指针会指向一个较高的下标位置。

2,队列中新增一个数据时,队尾的指针rear 会向上移动,也就是向下标大的方向。移除数据项时,队头指针 front 也会向下移动。

3,队列有一个maxSize(最大尺寸),当队尾和队头超过时最大尺寸时,队尾和队列循环回到初始位置,此队列也称循环队列。

代码如下:

//单向队列实现public class MyQueue {private Object[] queArray;//队列private int maxSize;//总大小private int head;//队首private int tail;//队尾private int nItems;//队列中的实际数目public MyQueue(int s) {this.maxSize = s;this.head = 0;this.tail = -1;this.queArray = new Object[maxSize];this.nItems = 0;}public void insert(int value) {if (isFull()) {System.out.println("队列已满");return;} else {//当尾端指向了顶部,循环会第一个元素if (tail == maxSize - 1) {tail = -1;}queArray[++tail] = value;nItems++;}}public void remove() {if (!isEmpty()) {queArray[head] = null;head++;if(head == maxSize) {head = 0;}nItems--;}}public Object peekFront() {return queArray[head];}public int getSize() {return nItems;}public Boolean isFull() {return (nItems == maxSize);}public Boolean isEmpty() {return (nItems == 0);}public Object[] getAll() {return queArray;}}
测试类

public class MyQueueTest {public static void main(String[] args) {// TODO Auto-generated method stubMyQueue mq = new MyQueue(10);mq.insert(1);mq.insert(2);mq.insert(5);mq.insert(9);mq.insert(11);mq.insert(15);mq.insert(19);mq.insert(21);mq.insert(25);mq.insert(29);mq.remove();mq.remove();mq.insert(33);mq.insert(37);mq.remove();mq.remove();Object[] queue = mq.getAll();for (Object obj : queue) {System.out.println(obj == null ? null:obj.toString());}}}

三、优先级队列

优先级队列(priority queue)是比栈和队列更专用的数据结构,在优先级队列中,数据项按照关键字进行排序,关键字最小(或者最大)的数据项往往在队列的最前面,而数据项在插入的时候都会插入到合适的位置以确保队列的有序。

优先级队列 是0个或多个元素的集合,每个元素都有一个优先权,对优先级队列执行的操作有:

  (1)查找

  (2)插入一个新元素

  (3)删除

一般情况下,查找操作用来搜索优先权最大的元素,删除操作用来删除该元素 。对于优先权相同的元素,可按先进先出次序处理或按任意优先权进行。

这里我们用数组实现优先级队列,这种方法插入比较慢,但是它比较简单,适用于数据量比较小并且不是特别注重插入速度的情况。

public class PriorityQue {    private int maxSize;    private int[] priQueArray;    private int nItems;         public PriorityQue(int s){        maxSize = s;        priQueArray = new int[maxSize];        nItems = 0;    }         //插入数据    public void insert(int value){        int j;        if(nItems == 0){            priQueArray[nItems++] = value;        }else{            j = nItems -1;            //选择的排序方法是插入排序,按照从大到小的顺序排列,越小的越在队列的顶端            while(j >=0 && value > priQueArray[j]){                priQueArray[j+1] = priQueArray[j];                j--;            }            priQueArray[j+1] = value;            nItems++;        }    }         //移除数据,由于是按照大小排序的,所以移除数据我们指针向下移动    //被移除的地方由于是int类型的,不能设置为null,这里的做法是设置为 -1    public int remove(){        int k = nItems -1;        int value = priQueArray[k];        priQueArray[k] = -1;//-1表示这个位置的数据被移除了        nItems--;        return value;    }         //查看优先级最高的元素    public int peekMin(){        return priQueArray[nItems-1];    }         //判断是否为空    public boolean isEmpty(){        return (nItems == 0);    }         //判断是否满了    public boolean isFull(){        return (nItems == maxSize);    } }

原创粉丝点击