队列是一种先进先出 的运算受限的线性结构,在一端进入入队插入 操作,另一端进行出队删除操作。

代码实现
接口定义
java
public interface Queue<E> {
/**
* 入队
*
* @param e 离队
*/
void enqueue(E e);
/**
* 离队
*
* @return 返回出队元素
*/
E dequeue();
/**
* 返回队列是否为空
*
* @return 返回结果
*/
boolean isEmpty();
/**
* 读取对头
*
* @return 返回元素
*/
E getHead();
/**
* 检查元素是否为空指针
* @param e 元素
*/
default void check(E e) {
if (e == null) {
throw new NullPointerException();
} }}
顺序表
队列的实现的难点在于顺序表,由于做循环列表,所以指针 front 和 rear 都设置为0

从该图可以看出,仅仅靠front==rear
只能说明队列为空或者是满队列。
所以通过判断0号数据或数组最后一位元素为空,来判断队列为空。
而满队列有两种情况:
rear + (elementData.length - front) == elementData.length
,如front=1,rear=1,则1+(7-1)=7。front == 0 && rear == elementData.length
,如[0,1,2,3,4,5,6]
,front = 0, rear = 7,则:7+(7-0)= 14,不满足条件1。所以需要条件2
在实现的队列拓展时候,将front重置为0,rear重置为旧数组的长度
java
package com.silvergravel.structure;
import java.util.Arrays;
import java.util.NoSuchElementException;
/**
* @author DawnStar
* @since 2025/8/3
*/
public class QueueSequence<E> implements Queue<E> {
protected Object[] elementData;
private int front = 0, rear = 0;
public QueueSequence(int initialCapacity) {
if (initialCapacity <= 0) {
this.elementData = new Object[10];
return;
} this.elementData = new Object[initialCapacity];
}
@Override
public void enqueue(E e) {
check(e);
// 这里实现二
// if (isEmpty()) {
// // 队空重置
// rear = 0;
// front = 0;
// elementData[rear] = e;
// rear++;
// return;
// }
// [0,1,2,3,4,5,6] // 如果 front = 3,rear =3 3+(7-3) =7 // 如果 front = 2,rear =2 2+(7-2) =7 // front = 0 ,rear =7 7+(7-0) = 14
boolean b = (rear + (elementData.length - front) == elementData.length) || (front == 0 && rear == elementData.length);
// 判断队列不为空且长度为7
if (b && !isEmpty()) {
// if (b) {
// 如果使用上述的注释实现二,那么 则不用使用 !isEmpty() grow();
} else if (rear == elementData.length) {
// [null,null,2,3,4,5,6]
rear = 0;
} elementData[rear] = e;
rear++;
}
@Override
@SuppressWarnings("unchecked")
public E dequeue() {
if (isEmpty()) {
throw new NoSuchElementException();
} if (front == elementData.length) {
front = 0;
E elementDatum = (E) elementData[front];
elementData[front] = null;
return elementDatum;
} else {
E elementDatum = (E) elementData[front];
elementData[front] = null;
front++;
return elementDatum;
} }
@Override
public boolean isEmpty() {
// rear == front 只能判断队空队满,但是不能判断是其中哪一种情况,所以再加上通过第一个元素为空来判断
return rear == front && elementData[0] == null;
}
@Override
@SuppressWarnings("unchecked")
public E getHead() {
if (front == elementData.length) {
return (E) elementData[0];
} return (E) elementData[front];
}
private void grow() {
// 当前值的1.5倍
int newSize = (elementData.length + 1) / 2 * 3;
if (front < rear) {
elementData = Arrays.copyOf(elementData, newSize);
return;
} final Object[] oldData = elementData;
elementData = new Object[newSize];
int length = oldData.length - front;
System.arraycopy(oldData, front, elementData, 0, length);
System.arraycopy(oldData, 0, elementData, length, rear);
// 重置指针数据
front = 0;
rear = oldData.length;
}
public int getFront() {
return front;
}
public int getRear() {
return rear;
}
public int size() {
return elementData.length;
}
@Override
public String toString() {
return "[" + String.join(",", Arrays.stream(elementData).map(String::valueOf).toList()) + "]";
}}
链表实现
java
/**
* 尾插法
*
* @author DawnStar
* @since 2025/8/3
*/
public class QueueLink<E> implements Queue<E> {
protected Node<E> head;
protected Node<E> rear;
public QueueLink() {
this.rear = new Node<>(null, null);
this.head = new Node<>(null, this.rear);
}
@Override
public void enqueue(E e) {
check(e);
rear.element = e;
Node<E> node = new Node<>(null, null);
rear.next = node;
rear = node;
}
@Override
public E dequeue() {
Node<E> next = head.next;
check(next.element);
head.next = next.next;
return next.element;
}
@Override
public boolean isEmpty() {
return head.next.element == null;
}
@Override
public E getHead() {
E element = head.next.element;
check(element);
return element;
}
protected static class Node<E> {
private E element;
private Node<E> next;
public Node(E element, Node<E> next) {
this.element = element;
this.next = next;
}
public E getElement() {
return element;
}
public void setElement(E element) {
this.element = element;
}
public Node<E> getNext() {
return next;
}
public void setNext(Node<E> next) {
this.next = next;
} }}
代码测试
java
/**
* @author DawnStar
* @since 2025/8/3
*/
public class QueueTest {
public static void main(String[] args) {
System.out.println("=".repeat(30) + "队列顺序表实现" + "=".repeat(50));
QueueSequence<String> queue = new QueueSequence<>(2);
queue.enqueue("A");
queue.enqueue("B");
queue.enqueue("C");
System.out.println(queue.dequeue());
System.out.println(queue.dequeue());
System.out.println("当前front指针:" + queue.getFront());
System.out.println("当前尾指针:" + queue.getRear());
System.out.println("长度:" + queue.size());
queue.enqueue("D");
queue.enqueue("E");
System.out.println("当前front指针:" + queue.getFront());
System.out.println("当前尾指针:" + queue.getRear());
System.out.println("长度:" + queue.size());
System.out.println(queue);
// 数组拓展
queue.enqueue("F");
System.out.println("长度:" + queue.size());
System.out.println(queue);
System.out.println("=".repeat(30) + "队列链表实现" + "=".repeat(50));
Queue<Integer> linkQueue = new QueueLink<>();
Stream.of(1, 2, 3, 4, 5, 6).forEach(linkQueue::enqueue);
List<Integer> list = new ArrayList<>();
while (!linkQueue.isEmpty()) {
list.add(linkQueue.dequeue());
} System.out.println(list.stream().map(String::valueOf).collect(Collectors.joining("、")));
}}
