队列(Queue)是限定只能在一端插入、另一端删除的线性表。允许删除的一端叫做队头(front),允许插入的一端叫做队尾(rear),没有元素的队列称为“空队列”。队列具有先进先出(FIFO)的特性。下面将介绍队列的两种实现方式:基于数组和基于链表的,其中数组使用的是循环队列的思想,如下图(图片来源于网络,如有侵权,请联系我,谢谢),有一个位置是不存储数据的,这样就能比较简单的区别队列满和队列空的状态,当front==tail时,队列空,当(tail+1)%数组的长度==front时,就是队列满。
1.数组实现
package test.queue;
//基于数组的队列实现:使用循环队列
public class MyQueueByArray {
private int[] a;
private int front;
private int rear;
public MyQueueByArray(int capacity) {
a=new int[capacity+1]; //有一个位置不存储数据,为了区别空和满的状态,牺牲一个空间
front=0;
rear=0;
}
//判空
public boolean isEmpty() {
return front==rear;
}
//判满
public boolean isFull() {
return ((rear+1)%a.length)==front;
}
//入队
public boolean add(int value) {
if(isFull()) {
System.out.println("队列满");
return false;
}
rear=(rear+1)%a.length;
a[rear]=value;
return true;
}
//出队
public int remove() {
if(isEmpty()) {
System.out.println("队列空");
return -1;
}
front=(front+1)%a.length;
return a[front];
}
//获取队头元素
public int peek() {
if(isEmpty()) {
System.out.println("队列空");
return -1;
}
return a[front];
}
public static void main(String[] args) {
MyQueueByArray queue=new MyQueueByArray(3);
//入队
queue.add(1);
queue.add(3);
queue.add(5);
queue.add(7);
//出队
while(!queue.isEmpty()) {
System.out.println(queue.remove());
}
}
}
2.链表实现
package test.queue;
//基于链表的队列实现:单向链表,尾插法,头部删除
public class MyQueueByLink {
//节点类
private class Node{
int data; //值域
Node next; //指针域,指向下一个节点
public Node(int value) {
data=value;
next=null;
}
}
private Node head; //头节点
private Node tail; //尾节点
//判空
public boolean isEmpty() {
return head==null;
}
//入队
public boolean add(int value) {
Node node=new Node(value);
//如果插入的是第一个节点,头节点,尾节点都是同一个节点
if(head==null) {
head=node;
tail=head;
return true;
}
//让尾节点指向新节点
tail.next=node;
//新节点成为新的尾节点
tail=node;
return true;
}
//出队
public int remove() {
if(isEmpty()) {
System.out.println("队列空");
return -1;
}
int value=head.data;
head=head.next; //删除头节点
return value;
}
public static void main(String[] args) {
MyQueueByLink queue=new MyQueueByLink();
//入队
queue.add(1);
queue.add(3);
queue.add(5);
//出队
while(!queue.isEmpty()) {
System.out.println(queue.remove());
}
}
}