關注 “弋凡”(YiFan)微信公衆號吧 記錄簡單筆記 做你的最愛
環形隊列圖
思路:
1,front
變量,初始值爲 0,指向隊列的第一個元素也是待取出的數據,
也就是說arr[front]是隊列的第一個元素
2,rear
變量,rear 初始值爲 0,指向待添加數據的位置,隊列添加數據時,因邏輯上的閉環,指針可能再次回到前面的位置,不能單一遞增處理,會出現角標越界異常,需通過取模來重新計算指針的值
3,當隊列滿時 條件是 (rear + 1) % maxsize == front
假如,maxsize 爲10,front爲0,rear爲9 此時隊列就滿了
4,當隊列爲空時,條件是 rear == front
5,rear指針指向待添加數據的元素位置,假設隊列內部數組的最大容量爲maxsize ,當rear指針指向maxsize -1時,實際該位置上並無數據,因此,隊列的最大容量只有maxsize -1,即隊列的最大有效數據個數爲maxsize -1,因爲預留一個位置
代碼
package com.yifan.linear;
import java.util.Scanner;
/**
* @Author YIFan
* @Date 2020/6/11 14:33
* @Version 1.0
*/
// 數組模擬環形隊列 取模考慮的是循環
public class CircleArrayQueue {
public static void main(String[] args) {
System.out.println("環形隊列...........");
CircleArrayQueeTest quee = new CircleArrayQueeTest(4);
Scanner scanner = new Scanner(System.in);
boolean loop = true;
while (loop){
System.err.println("(s) 顯示隊列信息");
System.err.println("(a) 添加數據到隊列");
System.err.println("(g) 從隊列取出數據");
System.err.println("(h) 顯示隊列頭數據");
System.err.println("(e) 退出程序");
char key = scanner.next().charAt(0);
switch (key){
case 'e':
loop = false;
break;
case 's':
try {
quee.showQueue();
} catch (Exception e) {
System.err.println(e.getMessage());
}
break;
case 'a':
try {
System.out.println("請輸入一個數據添加到隊列");
int i = scanner.nextInt();
quee.addQueue(i);
} catch (Exception e) {
System.err.println(e.getMessage());
}
break;
case 'g':
try {
System.out.println("取出:"+quee.getQueue());
} catch (Exception e) {
System.err.println(e.getMessage());
}
break;
case 'h':
try {
System.out.println("頭數據:"+quee.headQueue());
} catch (Exception e) {
System.err.println(e.getMessage());
}
break;
}
}
}
}
class CircleArrayQueeTest{
private int maxSize;//數組的最大容量
//front初始值爲 0,指向隊列的第一個元素也是待取出的數據,
private int front;//隊列頭
//rear 初始值爲 0,指向待添加數據的位置
private int rear;//隊列尾
private int[] arr;//數組用於存放數據 ,模擬隊列
//創建隊列的構造器
public CircleArrayQueeTest(int maxSize){
//這裏傳入 4 則有效數據只有3個 因爲設置了一個空的空間
this.maxSize = maxSize;
arr = new int[maxSize];
front = 0;// 指向隊列頭部 就是 隊列頭數據的前一個數據
rear = 0;// 隊列尾部 就是 隊列的最後一個數據
}
// 判斷隊列是否滿
public boolean isFull(){
return (rear+1) % maxSize == front;
}
// 判斷隊列是否爲null
public boolean isEmpty(){
return rear == front;
}
// 添加數據到隊列, 進隊列
public void addQueue(int num){
if(isFull()){
throw new RuntimeException("隊列已滿,加入不了");
}
//rear指向待添加數據的位置
arr[rear] = num;
// rear後移 必須考慮取模 避免越界
rear = (rear+1) % maxSize ;
}
// 獲取隊列的數據 ,出隊列
public int getQueue(){
if (isEmpty()){
throw new RuntimeException("隊列爲空,不能取值");
}
//front是指向待取出的數據位置
//1,先把front對應的值取出保存到臨時變量
//2,front後移 避免越界,考慮取模
//3,將臨時變量返回
int temp = arr[front];
front = (front+1) % maxSize;
return temp;
}
// 顯示隊列數據
public void showQueue(){
if (isEmpty()){
throw new RuntimeException("隊列爲空,沒有數據");
}
// 從front開始遍歷 遍歷多少個元素
for (int i = front; i < front+size() ; i++) {
System.out.printf("arr[%d]=%d\n",i%maxSize,arr[i%maxSize]);
}
}
// 顯示隊列頭數據
public int headQueue(){
if (isEmpty()){
throw new RuntimeException("隊列爲空,沒有數據");
}
return arr[front];
}
// 獲取隊列的有效個數
public int size(){
return (rear+maxSize-front)%maxSize;
}
}