数据结构-数组循环队列 ​ 作者:哇塞大嘴好帥

数据结构-数组循环队列 ​ 作者:哇塞大嘴好帥

​ 作者:哇塞大嘴好帥(哇塞大嘴好帅)


思路分析:

foot永远指向序列尾

head永远指向队列头部的后一位

​ 当队列满的时候,条件是: (head + 1) % 数组容量 == foot (详细介绍在最下方的代码分析)

​ 当队列为空的时 条件是:head == foot(详细介绍在最下方的代码分析)

​ 获取队列中有效数据个数 条件为:(head + 数组容量 - foot) % maxSize(详细介绍在最下方的代码分析)

此文章一定要耐心看完,我会把为什么这样做以及错误的示范,正确的代码都会给你讲解,让你彻底懂数组循环队列。

1.代码

package com.dazuizui;

import java.lang.reflect.Array;

public class QueueArray1 {
    public static void main(String[] args) {
        CircleArray circleArray = new CircleArray(5);
        System.out.println("======================");
        System.out.println("添加数据");
        circleArray.putArrayMember(12);
        circleArray.putArrayMember(13);
        circleArray.putArrayMember(13);
        circleArray.putArrayMember(14);
        circleArray.putArrayMember(15);
        System.out.println("======================");
        System.out.println("显示队列");
        circleArray.showListArray();
        System.out.println("======================");
        System.out.println("弹出");
        circleArray.numberExit();
        circleArray.numberExit();
        circleArray.numberExit();
        circleArray.numberExit();
        circleArray.numberExit();
        circleArray.numberExit();
        System.out.println("头部坐标"+circleArray.head+"foot:"+circleArray.foot);
        circleArray.putArrayMember(13);
        System.out.println("插入成功");
        System.out.println("头部坐标"+circleArray.head+"foot:"+circleArray.foot);
        circleArray.showListArray();
        circleArray.putArrayMember(13);
        circleArray.putArrayMember(13);
        System.out.println("======================");
        circleArray.showListArray();
    }
}

class CircleArray{
   private int maxSize    ; //数组长度
    int head    = 0;
    int foot    = 0;
   private int array[]    ; //可使用的数组空间

    /**
     * 进行初始化
     * @param maxSize 数组长度
     */
   public CircleArray(int maxSize){
       this.maxSize = maxSize;
       array = new int[maxSize];
   }

   //如果为空
    public boolean isNull(){
       return head == foot;
    }

    /**
     * 如果数列为满 如果 (5+1 % 6 == foot
     * @return
     */
    public boolean isMax(){
       return (head+1) % maxSize == foot;
    }

    /**
     * 添加数组
     */
    public void putArrayMember(int num){
        //0.判断数组是否为满
        if (isMax()){
            System.out.println("您的列表满了");
            return;
        }

        //1.将数据添加到进入
        array[head] = num;
        //2.将表头的数据前进一格
        head = (head + 1) % maxSize;
        System.out.println("长孺成功当前坐标为"+head);
        return;
    }

    /**
     * 显示所有数组
     */
    public void showListArray(){
        //0.判断是否为null
        if (isNull()){
            throw new RuntimeException("数组为null");
        }
        System.out.println("\n\n当前head:"+head+"foot"+foot+"有效数据"+vDataSize()+"数组大小"+maxSize);
        System.out.println(vDataSize()+foot+"/*/*");
        //遍历有效数据
        for (int i = foot; i < vDataSize()+foot ; i++) {
            System.out.println(array[i%maxSize]);
        }
    }

    /**
     * 查询有效数据
     * 假设 head 为 3
     *     foot 为 2
     *     大小  为 4
     */
    public int vDataSize(){
        return (head + maxSize - foot) % maxSize;
    }

    /**
     * 弹出数
     */
    public void numberExit(){
        //-0判断是否为null
        if (isNull()){
            System.out.println("数组为null");
            return;
        }
        System.out.println("当前坐标"+foot);
        //0.弹出数组的值
        System.out.println(array[foot]);
        //1.尾指针后移
        foot = (foot + 1) % maxSize;
        System.out.println("弹出后坐标"+foot);

    }
}

2.代码分析

构造方法初始化部分

    /**
     * 进行初始化
     * @param maxSize 数组长度
     */
   public CircleArray(int maxSize){
       this.maxSize = maxSize;
       array = new int[maxSize];
   }

​ 当我们传递5进此方法,该构造器就会把数组长度赋值给maxSize,并且创建一个长度为5的数组

接下来看是否为空方法

   //如果为空
    public boolean isNull(){
       return head == foot;
    }

​ 只要**(head+1) % maxSize == foot相等就证明数组为Null**

如以下表格进行理解

数组下标描述
01已经被弹出
12已经被弹出
23已经被弹出
3头指针和尾指针都在此处我们知道foot每次弹出后都会条件是: (foot+ 1) % 数组容量 head的算法是条件是: (head + 1) % 数组容量当他们相撞的时候就正常该队列没有元素了。

队列满载的方法

/**
 * 如果数列为满
 * @return
 */
public boolean isMax(){
   return (head+1) % maxSize == foot;
}

假设现在head为4 foot为0 maxSize为5将数值代入这时候算法为:

​ (4+1) % 5 = 0;

​ 这时候结果与foot相等,就证明了该队列为满载状态。

只有满载 (head+1) % maxSize == foot该条件才会满足,如果我们的队列没有满足他的可视图是这个样子的。

往列表增加元素方法

    /**
     * 添加数组
     */
    public void putArrayMember(int num){
        //0.判断数组是否为满
        if (isMax()){
            System.out.println("您的列表满了");
            return;
        }

        //1.将数据添加到进入
        array[head] = num;
        //2.将表头的数据前进一格
        head = (head + 1) % maxSize;
        System.out.println("长孺成功当前坐标为"+head);
        return;
    }

​ 首先它做了判断是否为满的,如果为满,那么停止添加。

​ 如果数组不为满,它会在 array[head] = num; ,当添加完数组他head会重新赋值将自己的下标后移一位。算法为:(head + 1) % maxSize

看弹出元素

/**
 * 弹出数
 */
public void numberExit(){
    //-0判断是否为null
    if (isNull()){
        System.out.println("数组为null");
        return;
    }
    //0.弹出数组的值
    System.out.println(array[foot]);
    //1.尾指针后移
    foot = (foot + 1) % maxSize;
}

​ 首先判断是否为null,如果为null,程序停止操作。

​ 如果不为NULL,那么就弹出array[foot]的数据,弹出之后经过(foot+1) % maxSize算法将自己坐标后移一位。

查询队列有效数据个数

/**
 * 查询有效数据
 * 假设 head 为 3
 *     foot 为 2
 *     大小  为 5
 */
public int vDataSize(){
    return (head + maxSize - foot) % maxSize;
}

​ 假设现在head为2 foot为4 大小为5 将数值代入:(2+5-4)%5 = 3 这时候算出来有效数据有3

查询队列数据

/**
 * 显示队列数据
 */
public void showListArray(){
    //0.判断是否为null
    if (isNull()){
        throw new RuntimeException("数组为null");
    }

    //遍历有效数据
    for (int i = foot; i < vDataSize()+foot ; i++) {
        System.out.println(array[i%maxSize]);
    }
}

​ 首先判断是否为Null,接下来注意for循环

​ 首先i = foot 因为foot代表列表尾巴,也就是说先进入的数据,接下来看 i < vDataSize()+foot 已知现在有效数据为3个,vDataSize()+foot = 7 foot = 4 也就是通过3次循环把队列中的3个有效数据打印出来。

第一次循环: i% maxSize = 4 这时候i=4,maxSize=5 把array数组第4个数据读取出来.

第二次循环: i% maxSize = 0 这时候i=5,maxSize=5 把array数组第0个数据读取出来.

第三次循环: i% maxSize = 1 这时候i=6,maxSize=5 把array数组第1个数据读取出来.

3.为什么数组中要空一个空间

​ 因为方便计算空出一个空间

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

哇塞大嘴好帅(DaZuiZui)

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值