数据结构-队列

概念

队列是一种特殊的线性表,特殊之处在于它只允许在表的前端(front)进行删除操作,而在表的后端(rear)进行插入操作,和栈一样,队列是一种操作受限制的线性表。进行插入操作的端称为队尾,进行删除操作的端称为队头。队列中没有元素时,称为空队列。

使用数组表示队列

队列

  • 上图是队列中依次添加0 1 2三个元素
  • front是队列的第一元素的前一个位置
  • rear是队列中的最后一个元素的位置
  • 当front=rear的时候队列为空
  • 取出元素从队列头开始取,如下图取出0元素
    取出一个元素

使用数组实现上面的队列代码:

package com.liouxb.data.structure;

/**
 * 队列
 *
 * @author liouwb
 */
public class QueueDemo {
    public static void main(String[] args) {

    }
}

/**
 * 使用数组实现队列
 */
class ArrayQueue {
    // 队列(集合)的最大长度
    private int maxSize;

    // 队列头
    private int front;

    // 队列尾
    private int rear;

    // 数据集合
    private int[] arrQueue;

    /**
     * 构造函数
     */
    public ArrayQueue(int maxSize) {
        this.maxSize = maxSize;
        this.arrQueue = new int[maxSize];
        // 指向队列头数据的前一个位置
        this.front = -1;
        // 最后一个数据的位置
        this.rear = -1;
    }

    /**
     * 判断队列是否已满
     *
     * @return
     */
    boolean isFull() {
        return this.rear == this.maxSize - 1;
    }

    /**
     * 判断队列是否为空
     *
     * @return
     */
    boolean isEmpty() {
        return this.rear == this.front;
    }

    /**
     * 向队列中添加数据
     */
    void addQueue(int param) {

        // 1、判断队列是否满
        if (isFull()) {
            System.out.println("队列已满,请等待。。。");
        }

        // 尾部向后移
        this.rear++;

        arrQueue[rear] = param;
    }

    /**
     * 从队列中获取数据
     */
    int popQueue() {
        if (isEmpty()) {
            throw new RuntimeException("队列为空");
        }

        // 头部后移
        this.front++;

        return this.arrQueue[front];
    }

    /**
     * 获取队列所有数据
     */
    void showAllQueue() {

        if (isEmpty()) {
            System.out.println("队列为空");
            return;
        }

        for (int i = 0; i < arrQueue.length; i++) {

            System.out.println(arrQueue[i]);
        }

    }
}

数组队列问题

环形队列

环形队列

判断环形队列满的方式

  1. 使用一个变量size做标记,添加元素size+1,取出元素size-1
  2. 使用n-1个空间表示
  3. 使用标识位flag来表示最后一次的操作状态,fornt=rear,flag添加的话表示队列是满的,flag是取出操作的话则表示队列为空

使用数组实现环形队列代码

package com.liouxb.data.structure;

/**
 * 环形队列
 * 数组实现
 *
 * @author liouwb
 */
public class QueueCircleDemo {
    public static void main(String[] args) {

    }
}

/**
 * 使用数组实现环形队列
 */
class CircleArrayQueue {
    // 队列(集合)的最大长度
    private int maxSize;

    // 队列头
    private int front;

    // 队列尾
    private int rear;

    // 数据集合
    private int[] arrQueue;

    /**
     * 构造函数
     */
    public CircleArrayQueue(int maxSize) {
        this.maxSize = maxSize;
        this.arrQueue = new int[maxSize];
        // 指向队列头数据的第一个元素的位置
        this.front = 0;
        // 最后一个元素的后一个位置
        this.rear = 0;
    }

    /**
     * 环形队列判断是否已满
     *
     * @return
     */
    boolean isFull() {
        return (this.rear + 1) / this.maxSize == this.front;
    }

    /**
     * 判断队列是否为空
     *
     * @return
     */
    boolean isEmpty() {
        return this.rear == this.front;
    }

    /**
     * 向队列中添加数据
     */
    void addQueue(int param) {

        // 1、判断队列是否满
        if (isFull()) {
            System.out.println("队列已满,请等待。。。");
        }

        arrQueue[rear] = param;

        // 尾部向后移
        this.rear = (rear + 1) % maxSize;


    }

    /**
     * 从队列中获取数据
     */
    int popQueue() {
        if (isEmpty()) {
            throw new RuntimeException("队列为空");
        }

        // 1、用一个临时变量保存要取的元素
        // 2、front后移
        // 3、返回临时变量
        int temp = 0;
        temp = this.arrQueue[front];

        // 头部后移
        this.front = (this.front + 1) / maxSize;

        return temp;
    }

    /**
     * 获取队列所有数据
     */
    void showAllQueue() {

        if (isEmpty()) {
            System.out.println("队列为空");
            return;
        }

        // 从front开始遍历:需要遍历有效数据个数
        int count = count();

        for (int i = front; i < front + count; i++) {

            System.out.println(arrQueue[i]);
        }

    }

    /**
     * 获取环形队列有效元素个数
     * (rear+maxSize-front)%maxSize
     *
     * @return
     */
    private int count() {
        return (rear + maxSize - front) % maxSize;
    }
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值