數據結構和算法(2)-----隊列

一、基本介紹

  • 隊列是一個有序列表,可以用數組鏈表來實現
  • 遵循先入先出的原則,即先存入隊列的數據,要先取出;後存入隊列的數據,要後取出
  • 示意圖:

二、數組模擬隊列

思路:

  • 隊列本身是有序列表,若使用數組的結構來存儲隊列的數據,則隊列數組的聲明如下圖,其中maxSize是該隊列的最大容量。

  • 因爲隊列的輸出,輸入是分別從隊頭和隊尾來處理,因此需要兩個變量front和rear分別記錄隊列前後端的下標,front會隨着數據輸出而改變,而rear則是隨着數據輸入而改變。
  • 我們將數據存入隊列時稱爲addQueue,addQueue的處理需要有兩個步驟,分別是:將尾指針往後移,rear+1;若尾指針rear小於隊列的最大下標maxSize-1,則將數據存入rear所指的數組元素中,否則無法存入數據。
  • 隊列初始:front和rear均爲-1,front指向隊頭的前一個元素,rear指向隊尾元素
  • 隊列爲空:front==rear
  • 隊列爲滿:rear==maxSize-1

代碼實現:

package com.atguigu.queue;

public class ArrayQueue {
	private int maxSize;
	private int front;
	private int rear;
	private int [] arr;
	
	//構造函數,初始化隊列
	public ArrayQueue(int maxSize) {
		this.maxSize = maxSize;
		arr=new int [this.maxSize];
		front=-1;
		rear=-1;
	}
	
	
	//判斷隊列是否爲滿
	public boolean isFull(){
		if(rear==maxSize-1){
			return true;
		}else{
			return false;
		}
	}
	
	
	//判斷隊列是否爲空
	public boolean isEmpty(){
		if(front==rear){
			return true;
		}else{
			return false;
		}
	}
	
	
	//入隊
	public void addQueue(int n){
		if(this.isFull()==false){
			rear++;
			arr[rear]=n;
		}else{
			System.out.println("隊列已滿");
		}
	}
	
	
	//出隊
	public int getQueue(){
		if(this.isEmpty()==false){
			front++;
			return arr[front];
		}else{
			throw new RuntimeException("隊列爲空");
		}
	}
	
	
	//打印隊列內容
	public void showQueue(){
		if(this.isEmpty()){
			System.out.println("隊列爲空");
		}else{
			System.out.print("[");
			for(int i=front+1;i<=rear;i++){
				if(i!=rear){
					System.out.print(arr[i]+",");
				}else{
					System.out.print(arr[i]);
				}
			}
			System.out.print("]");
			System.out.println();
		}
	}
	
	
	//獲取隊頭元素
	public int headQueue(){
		if(this.isEmpty()==true){
			throw new RuntimeException("隊列爲空");
		}else{
			return arr[front+1];
		}
	}
}

測試代碼:

package com.atguigu.queue;

public class ArrayQueueDemo {
	public static void main(String[] args) {
		ArrayQueue arrayQueue=new ArrayQueue(5);
		
		arrayQueue.showQueue();
		
		System.out.println("-------------------------------------------------");
		arrayQueue.addQueue(34);
		System.out.print("隊列的元素:");
		arrayQueue.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue.headQueue());
		
		System.out.println("-------------------------------------------------");
		arrayQueue.addQueue(45);
		System.out.print("隊列的元素:");
		arrayQueue.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue.headQueue());
		
		System.out.println("-------------------------------------------------");
		arrayQueue.addQueue(65);
		System.out.print("隊列的元素:");
		arrayQueue.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue.headQueue());
		
		System.out.println("-------------------------------------------------");
		arrayQueue.addQueue(86);
		System.out.print("隊列的元素:");
		arrayQueue.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue.headQueue());
		
		System.out.println("-------------------------------------------------");
		arrayQueue.addQueue(93);
		System.out.print("隊列的元素:");
		arrayQueue.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue.headQueue());
		
		System.out.println("-------------------------------------------------");
		arrayQueue.addQueue(37);
		System.out.print("隊列的元素:");
		arrayQueue.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue.headQueue());
		
		System.out.println("-------------------------------------------------");
		int temp1=arrayQueue.getQueue();
		System.out.println("取出的元素是:"+temp1);
		System.out.print("隊列的元素:");
		arrayQueue.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue.headQueue());
		
		System.out.println("-------------------------------------------------");
		int temp2=arrayQueue.getQueue();
		System.out.println("取出的元素是:"+temp2);
		System.out.print("隊列的元素:");
		arrayQueue.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue.headQueue());
		
		System.out.println("-------------------------------------------------");
		int temp3=arrayQueue.getQueue();
		System.out.println("取出的元素是:"+temp3);
		System.out.print("隊列的元素:");
		arrayQueue.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue.headQueue());
		
		System.out.println("-------------------------------------------------");
		int temp4=arrayQueue.getQueue();
		System.out.println("取出的元素是:"+temp4);
		System.out.print("隊列的元素:");
		arrayQueue.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue.headQueue());
		
		System.out.println("-------------------------------------------------");
		arrayQueue.addQueue(100);
		System.out.print("隊列的元素:");
		arrayQueue.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue.headQueue());

	}

}

效果圖:

問題分析:

  • 目前數組使用一次就不能繼續使用了,沒有達到複用的效果
  • 將這個數組使用算法,改進成一個環形的隊列(取模)

三、數組模擬環形隊列

思路:

對前面的數組模擬隊列的優化,充分利用數組,因此將數組看做是一個環形的(通過取模的方式來實現)

在環形隊列中,如圖b所示,隊列爲滿,則front==rear;如圖c所示,隊列爲空時,則front==rear。因此無法判斷隊列爲滿或爲空,處理方法:少用一個元素空間,約定以“隊列頭指針在隊尾指針的下一位置(值環形的下一個位置)上”作爲隊滿的標誌

分析:

  • front變量的含義做一個調整:front指向隊列的第一個元素,也就是arr[front]就是隊列的第一個元素,front的初始值爲0
  • rear變量的含義做一個調整:rear指向隊列的最後一個元素的後一個位置,因爲希望它空出一個空間作爲約定,rear的初始值爲0
  • 隊列爲滿:(rear+1)%maxSize==front
  • 隊列爲空:rear==front
  • 隊列中元素的個數(對長):(rear-front+maxSize)%maxSize

代碼實現:

package com.atguigu.queue;

public class ArrayQueue1 {
	private int maxSize;
	private int front;
	private int rear;
	private int [] arr;
	
	
	//構造函數,初始化隊列
	public ArrayQueue1(int maxSize) {
		this.maxSize = maxSize;
		arr=new int [this.maxSize];
		front=0;
		rear=0;
	}
	
	//判斷隊列是否已滿
	public boolean isFull(){
		if((this.rear+1)%this.maxSize==front){
			return true;
		}else{
			return false;
		}
	}
	
	
	//判斷隊列是否爲空
	public boolean isEmpty(){
		if(this.rear==this.front){
			return true;
		}else{
			return false;
		}
	}
	
	
	//入隊
	public void addQueue(int n){
		if(this.isFull()){
			System.out.println("隊列已滿,不可添加元素");
		}else{
			arr[rear]=n;
			rear=(rear+1)%this.maxSize;    //將rear後移一位,這裏必須考慮環形隊列(取模)
		}
	}
	
	
	//出隊
	public int getQueue(){
		if(this.isEmpty()){
			throw new RuntimeException("隊列爲空,不可取出元素");
		}else{
			int temp=arr[front];                    //1.先把front對應的值保存到一個臨時變量
			front=(front+1)%maxSize;         //2.將front後移一位
			return temp;                                 //3.將臨時變量返回
		}
	}
	
	
	
	//獲取隊列長度
	public int getLength(){
		return (rear-front+maxSize)%maxSize;
	}
	
	
	//打印隊列元素
	public void showQueue(){
		if(this.isEmpty()){
			System.out.println("隊列爲空,無法顯示隊列");
		}else{
			System.out.print("[");
			for(int i=front;i<(this.getLength()+this.front);i++){
				if(i!=(this.getLength()+this.front-1)){
					System.out.print(arr[i%this.maxSize]+",");
				}else{
					System.out.print(arr[i%this.maxSize]);
				}
			}
			System.out.println("]");
		}
	}
	
	
	//獲取隊頭元素
	public int headQueue(){
		if(this.isEmpty()){
			throw new RuntimeException("隊列爲空,沒有隊頭元素");
		}else{
			return arr[front];
		}
	}
}
package com.atguigu.queue;

public class ArrayQueueDemo1 {
	public static void main(String[] args) {
		ArrayQueue1 arrayQueue1=new ArrayQueue1(5);
		System.out.println("隊列的初始長度:"+arrayQueue1.getLength());
		
		System.out.println("-------------------------------------------------");
		arrayQueue1.addQueue(34);
		System.out.println("隊列的當前長度:"+arrayQueue1.getLength());
		System.out.print("隊列的元素:");
		arrayQueue1.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue1.headQueue());
		
		System.out.println("-------------------------------------------------");
		arrayQueue1.addQueue(78);
		System.out.println("隊列的當前長度:"+arrayQueue1.getLength());
		System.out.print("隊列的元素:");
		arrayQueue1.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue1.headQueue());
		
		System.out.println("-------------------------------------------------");
		arrayQueue1.addQueue(43);
		System.out.println("隊列的當前長度:"+arrayQueue1.getLength());
		System.out.print("隊列的元素:");
		arrayQueue1.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue1.headQueue());
		
		System.out.println("-------------------------------------------------");
		arrayQueue1.addQueue(88);
		System.out.println("隊列的當前長度:"+arrayQueue1.getLength());
		System.out.print("隊列的元素:");
		arrayQueue1.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue1.headQueue());
		
		System.out.println("-------------------------------------------------");
		arrayQueue1.addQueue(22);
		System.out.println("隊列的當前長度:"+arrayQueue1.getLength());
		System.out.print("隊列的元素:");
		arrayQueue1.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue1.headQueue());
		
		System.out.println("-------------------------------------------------");
		int temp1=arrayQueue1.getQueue();
		System.out.println("取出的元素是:"+temp1);
		System.out.println("隊列的當前長度:"+arrayQueue1.getLength());
		System.out.print("隊列的元素:");
		arrayQueue1.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue1.headQueue());
		
		System.out.println("-------------------------------------------------");
		int temp2=arrayQueue1.getQueue();
		System.out.println("取出的元素是:"+temp2);
		System.out.println("隊列的當前長度:"+arrayQueue1.getLength());
		System.out.print("隊列的元素:");
		arrayQueue1.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue1.headQueue());
		
		System.out.println("-------------------------------------------------");
		int temp3=arrayQueue1.getQueue();
		System.out.println("取出的元素是:"+temp3);
		System.out.println("隊列的當前長度:"+arrayQueue1.getLength());
		System.out.print("隊列的元素:");
		arrayQueue1.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue1.headQueue());
		
		System.out.println("-------------------------------------------------");
		int temp4=arrayQueue1.getQueue();
		System.out.println("取出的元素是:"+temp4);
		System.out.println("隊列的當前長度:"+arrayQueue1.getLength());
		System.out.print("隊列的元素:");
		arrayQueue1.showQueue();
//		System.out.println("隊列的隊頭元素:"+arrayQueue1.headQueue());
		
		System.out.println("-------------------------------------------------");
		arrayQueue1.addQueue(100);
		System.out.println("隊列的當前長度:"+arrayQueue1.getLength());
		System.out.print("隊列的元素:");
		arrayQueue1.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue1.headQueue());
		
		System.out.println("-------------------------------------------------");
		arrayQueue1.addQueue(200);
		System.out.println("隊列的當前長度:"+arrayQueue1.getLength());
		System.out.print("隊列的元素:");
		arrayQueue1.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue1.headQueue());
		
		System.out.println("-------------------------------------------------");
		arrayQueue1.addQueue(300);
		System.out.println("隊列的當前長度:"+arrayQueue1.getLength());
		System.out.print("隊列的元素:");
		arrayQueue1.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue1.headQueue());
		
		System.out.println("-------------------------------------------------");
		arrayQueue1.addQueue(400);
		System.out.println("隊列的當前長度:"+arrayQueue1.getLength());
		System.out.print("隊列的元素:");
		arrayQueue1.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue1.headQueue());
		
		System.out.println("-------------------------------------------------");
		arrayQueue1.addQueue(500);
		System.out.println("隊列的當前長度:"+arrayQueue1.getLength());
		System.out.print("隊列的元素:");
		arrayQueue1.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue1.headQueue());
		
		System.out.println("-------------------------------------------------");
		int temp5=arrayQueue1.getQueue();
		System.out.println("取出的元素是:"+temp5);
		System.out.println("隊列的當前長度:"+arrayQueue1.getLength());
		System.out.print("隊列的元素:");
		arrayQueue1.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue1.headQueue());
		
		System.out.println("-------------------------------------------------");
		int temp6=arrayQueue1.getQueue();
		System.out.println("取出的元素是:"+temp6);
		System.out.println("隊列的當前長度:"+arrayQueue1.getLength());
		System.out.print("隊列的元素:");
		arrayQueue1.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue1.headQueue());
		
		System.out.println("-------------------------------------------------");
		int temp7=arrayQueue1.getQueue();
		System.out.println("取出的元素是:"+temp7);
		System.out.println("隊列的當前長度:"+arrayQueue1.getLength());
		System.out.print("隊列的元素:");
		arrayQueue1.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue1.headQueue());
		
		System.out.println("-------------------------------------------------");
		int temp8=arrayQueue1.getQueue();
		System.out.println("取出的元素是:"+temp8);
		System.out.println("隊列的當前長度:"+arrayQueue1.getLength());
		System.out.print("隊列的元素:");
		arrayQueue1.showQueue();
//		System.out.println("隊列的隊頭元素:"+arrayQueue1.headQueue());
		
		System.out.println("-------------------------------------------------");
		arrayQueue1.addQueue(1000);
		System.out.println("隊列的當前長度:"+arrayQueue1.getLength());
		System.out.print("隊列的元素:");
		arrayQueue1.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue1.headQueue());
		
		System.out.println("-------------------------------------------------");
		arrayQueue1.addQueue(2000);
		System.out.println("隊列的當前長度:"+arrayQueue1.getLength());
		System.out.print("隊列的元素:");
		arrayQueue1.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue1.headQueue());
		
		System.out.println("-------------------------------------------------");
		arrayQueue1.addQueue(3000);
		System.out.println("隊列的當前長度:"+arrayQueue1.getLength());
		System.out.print("隊列的元素:");
		arrayQueue1.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue1.headQueue());
		
		System.out.println("-------------------------------------------------");
		arrayQueue1.addQueue(4000);
		System.out.println("隊列的當前長度:"+arrayQueue1.getLength());
		System.out.print("隊列的元素:");
		arrayQueue1.showQueue();
		System.out.println("隊列的隊頭元素:"+arrayQueue1.headQueue());
	}
}

效果圖:

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章