1. 程式人生 > >Java陣列模擬佇列

Java陣列模擬佇列

佇列

先進先出

什麼意思呢?
我的理解:佇列就是一個數組(不包含連結串列),然後我們給它施加一個存資料和取資料的規則
當只允許從一端存資料,從另一端取資料的陣列,就是佇列,我們要做的就是給這個陣列施加我們制定的規則

不理解就上圖

圖解步驟:
【圖(a)】有一個長度為5的陣列,定義頭部標誌和尾部標誌
【圖(b)】按順序插入e1,e2,e3資料,插入資料從尾部插入,此時頭部標誌不變,插入一個數據,尾部標誌就加1
【圖(c)】取元素就只能從頭部取,每取一個數據,頭部標誌就加一
【圖(d)】這樣就形成了先進先出的規則
再不理解多思考,多敲兩遍程式碼,或者講一遍給別人聽

程式碼實現

public class ArrayQueue {
    //最大長度
    int maxSize;
    //定義一個數組,儲存資料
    private int[] queue;
    //定義對頭和隊尾標誌
    private int front;
    private int rear;
    //初始化一個數組
    public void init(int maxSize){
        front = -1;
        rear = -1;
        this.maxSize = maxSize;
        this.queue = new int[maxSize];
    }
    //判斷對滿
    public boolean isFull(){
         return rear == maxSize-1;
    }
    //判斷隊空
    public boolean isEnpty(){
        return front == rear;
    }
    //加入資料,只能從隊頭加入
    public void add(int num){
        if(isFull()){
            System.out.println("佇列滿了,插入失敗");
            return;
        }
        //要理清楚先後順序
        rear++;
        queue[rear] = num;
    }
    //取資料,只能從隊尾取
    public int get(){
        if(isEnpty()){
            System.out.println("佇列為空");
            //陣列初始化之後預設值就是0
            return 0;
        }
        front++;
        return queue[front];
    }
    //檢視隊頭元素
    public int showFront(){
        if(isEnpty()){
            System.out.println("佇列為空");
            //陣列初始化之後預設值就是0
            return 0;
        }
        return queue[front+1];
    }
    //遍歷所有數
    public void showAll(){
        if(isEnpty()){
            System.out.println("佇列為空");
            //陣列初始化之後預設值就是0
            return;
        }
        System.out.println("顯示佇列:======");
        for(int i = front+1; i <= rear; i++){
            System.out.println(queue[i]);
        }
        System.out.println("===============");
    }
}

【程式碼改進】
使用這個佇列,你會覺得很難受,因為你定義了它的長度,它的長度就不能改變了,我們可以設計一個長度可以增加的佇列

【設計思路】
當rear==maxSize,即陣列滿了的時候,我們新建一個數組,比原陣列長一倍,然後將原陣列的值賦值到新陣列

【程式碼實現】
我們只要修改add方法的程式碼

public void add(int num){
    if(isFull()){
        //新建一個長度為原來兩倍的陣列
        int[] newQueue = new int[maxSize*2];
        //原陣列賦值到新陣列
        for(int i = front+1; i <= rear; i++){
            newQueue[i] = queue[i];
        }
        rear++;
        queue[rear] = num;
        return;
    }
    rear++;
    queue[rear] = num;
}

【思考】
其實程式碼還有很多改進空間
1.比如這裡我們寫死了只能使用int型別的陣列,那麼我們能不能將型別像引數一樣,在初始化佇列的時候再確認呢?這裡可以用到泛型知識
2.再比如取資料的時候,當這個數不存在的時候我們返回的是預設值0,能不能不返回0,也能使程式碼正常結束呢,這裡可以用到異常知識

資料結構的改進
我們會發現,如果使用這種結構來建立佇列,當取出資料後,front前面的空間就不能進行操作了,造成了大量的空間浪費,這個時候我們可以
將順序佇列假象成一個