20210329-算法学习-队列
1.队列使用场景(银行排队案例):
图1.1
1.1.队列介绍:
队列是一种特殊的现行列表,他只允许在表的前端(front)进行删除操作,而表的后端(rear)进行插入操作。
当进行插入操作的端称为队尾,进行删除操作的端称为队头,当队列中没有元素时,称为空队列。
在队列这种数据结构中个,最先插入的元素将是最先被删除的元素,反之最后插入的元素将是最后被删除的元素,因此队列又称为 "先进先出" (FIFO-first in first out) 的线性表。
队列空的条件:front=rear
队列满的条件:rear=MAXSIZE
1.2.队列的链表实现:
在队列的形成过程中,可以利用线性链表的原理,来生成一个队列。
基于链表的队列,要动态创建和删除节点,效率较低,但是可以动态增长。
队列采用的FIFO(first in first out),新元素(等待进入队列的元素) 总是被插入到链表的尾部,而读取的时候总是从链表的头部开始读取,每次读取一个元素,释放一个元素。
所谓动态创建,动态释放,因而也不存在溢出等问题,由于链表由结构体间接而成,遍历也方便
1.3.队列的数组实现:
队列本身就是有序列表,若要使用数组的结构来存储队列的数据,则队列数组的声明如下(图1.2),其中 maxSize是该队列的最大容量。
因为队列的输出,输入的是分别从前后端来处理的,因此需要两个变量 front和rear 分别记录队列前后的下标,front 会随着数据输出而改变,而rear 则是随着数据输入而改变的
图1.2
1.4.数组模拟队列的基本思想:
当数组表示队列的时候,该数组只能被使用一次
队列是一个有序列表,可以用数组或链表表示
遵循先入先出的原则,即先存入队列中的数据,要先取出,后存入的数据后取出
定义队列的时候,主要有三个参数(front头,rear尾,maxSize),maxSize即为队列的最大容量
判断队列是不是空,根据 rear==front true的话 则这个队列为空
判断该队列是不是已经存满数据 rear==arr[maxSize-1] true的话 则表明这个队列已经满了
当给该队列添加数据的时候,需要rear++ front不变
当从该队列中取出数据的时候,则需要 front++ rear不变
2.代码:
package com.atAlgorithmTest;
/**
* @Author: lisongtao
* @Date: 2021/3/29 14:43
*/
import com.sun.jmx.remote.internal.ArrayQueue;
import java.util.Scanner;
/**
* @ClassName QueryArray
* @Description银行排队-队列
* @Author DELL
* @Date 2021/03/29 14:43
**/
public class QueueArray {
public static void main(String[] args) {
//创建一个队列
QueueArrayCreate queueArray = new QueueArrayCreate(3);
char key = ' ';
Scanner scanner = new Scanner(System.in);
boolean loop = true;
while(loop){
System.out.println("s(show): 显示队列");
System.out.println("e(exit): 退出队列");
System.out.println("a(add): 添加数据到队列");
System.out.println("g(get): 从队列中取出数据");
System.out.println("h(head): 查看队列头的数据");
key = scanner.next().charAt(0);
switch (key){
case 's':
queueArray.showQueue();
break;
case 'a':
System.out.println("输入一个数");
int i = scanner.nextInt();
queueArray.addQueue(i);
break;
case 'g':
try {
int res = queueArray.getQueue();
System.out.println("取出的数据是: "+res);
} catch (Exception e) {
System.out.println(e.getMessage());
}
break;
case 'h':
try {
int res = queueArray.headQueue();
System.out.println("队列头数据是: "+res);
} catch (Exception e) {
System.out.println(e.getMessage());
}
break;
case 'e':
scanner.close();
loop=false;
break;
default:
break;
}
}
System.out.println("程序退出");
}
}
class QueueArrayCreate{
private int maxSize;//表示数组的最大容量
private int front;//队列头
private int rear;//队列尾
private int[] arr;//该数组用来存放数据,模拟队列
//创建一个队列构造器
public QueueArrayCreate(int arrMaxSize){
maxSize = arrMaxSize;
arr = new int[maxSize];
front = -1;//指向队列头部(队列头的前一个位置)
rear = -1;//指向队列尾部(队列的最后一个数据)
}
//判断队列是否已满
public boolean isFull(){
return rear == maxSize-1;
}
//需要判断队列是否为空
public boolean isEmpty(){
return rear == front;
}
//添加数据到队列中
public void addQueue(int n){
//判断队列是否已满
if(isFull()){
System.out.println("队列已满,不能再添加数据");
return;
}
rear++;//队列后移
arr[rear] = n;
}
//获取队列的数据,出队列
public int getQueue(){
if (isEmpty()){
//当队列为空时,取不出数据
throw new RuntimeException("队列为空,不能取出数据");
}
front++;//front后移
return arr[front];
}
//显示队列
public void showQueue(){
if (isEmpty()){
System.out.println("队列为空,没有数据");
return;
}
for (int i = 0; i<arr.length; i++){
System.out.printf("arr[%d]=%d\n",i,arr[i]);
}
}
//显示队列头的数据
public int headQueue(){
if (isEmpty()) {
System.out.println("队列为空,没有数据");
}
return arr[front+1];
}
}

浙公网安备 33010602011771号