稀疏数组和队列

298 阅读2分钟

1.稀疏数组

当一个数组中大部分元素为0,或者为同一个值得数组时,可以使用稀疏数组来保存该数组。

稀疏数组的处理方法是:
1)记录数组一共有几行几列,有多少个不同的值
2)把具有不同值的元素的行列及值记录在一个小规模的数组中,从而缩小程序的规模
例如数组array[6][7]:
\begin{array}{|c|c|c|c|c|c|}
     \hline
     0 & 0 & 0 & 22 & 0 & 0 & 15\\
     \hline
     0 & 11 & 0 & 0 & 0 & 17 & 0 \\
     \hline
     0 & 0 & 0 & -6 & 0 & 0 & 0 \\
     \hline
     0 & 0 & 0 & 0 & 0 & 39 & 0 \\
     \hline
     91 & 0 & 0 & 0 & 0 & 0 & 0 \\
     \hline
     0 & 0 & 28 & 0 & 0 & 0 & 0 \\
     \hline
     
     \end{array}
可以转化为稀疏数组array[9][3]
\begin{array}{|c|c|c|}
    \hline
    \text{行} & \text{列} & \text{值} \\
    \hline
    6 & 7 & 8 \\
    \hline
    0 & 3 & 22 \\
    \hline
    0 & 6 & 15 \\
    \hline
    1 & 1 & 11 \\
    \hline
    1 & 5 & 17 \\
    \hline
    2 & 3 & -6 \\
    \hline
    3 & 5 & 39 \\
    \hline
    4 & 0 & 91 \\
    \hline
    5 & 2 & 28 \\
    \hline
    \end{array}

2.队列

2.1 队列介绍

1)队列是一个有序列表,可以用数组或是链表实现
2)遵循先入先出的原则,即:先存入队列的数据,要先取出;后存入的要后取出

2.2 数组模拟环形队列思路

思路如下:
1.指针front指向队列的第一个元素。初始值为0
2.指针rear指向队列最后一个元素的后一个位置,因为希望空出一个空间作为约定。rear的初始值为0
3.当队列满时,条件是(rear+1) % maxSize = front;
4.当队列为空的条件是rear == front;
5.如此分析,队列中有效的数据的个数是(rear + maxSize -front) % maxSize;
6.由简单队列修改为环形队列

2.3 代码

2.3.1 数组不可重复

class ArrayQueue {

    // 设置指针指向队列头部的前一个位置
    private int front = -1;

    // 设置指针指向队列的尾部
    private int rear = -1;

    // 设置队列的最大容量
    private int maxSize;

    // 用于存放数据模拟队列的数组
    private int[] arr;

    public ArrayQueue(int maxSize){
        this.maxSize = maxSize;
        this.arr = new int[maxSize];
    }

    /**
     * 用于添加数据进队列
     * @param n
     */
    public void add(int n){
        if (ifFull()){
            System.out.println("队列已满!");
            return;
        }
        rear++;
        arr[rear] = n;

    }

    /**
     *
     * @return
     */
    public int get(){
        if (ifEmpty()){
            throw new RuntimeException("队列为空!");
        }
        front++;
        return arr[front];
    }

    /**
     * 显示队列
     */
    public void show(){
        if (ifEmpty()){
            System.out.println("队列是空的!");
            return;
        }
        for (int i = front+1; i<= rear; i++){
            System.out.printf(arr[i] + "\t");
        }
        System.out.println();
    }

    /**
     * 显示头部数据
     */
    public void showHead(){
        System.out.println(arr[front+1]);
    }


    /**
     *
     * @return rear
     */
    public boolean ifFull(){
        return rear == maxSize-1;
    }

    /**
     * 用于判断队列是否为空
     * @return
     */
    public boolean ifEmpty(){
        return front == rear;
    }
}

2.3.2 数组模拟环形队列

class ArrayQueue2 {

    // 设置队列最大容量
    private int maxSize;
    // 设置指针指向队列头部位置
    private int front;
    // 设置指针指向队列尾部的后一个位置
    private int rear;

    private int[] arr;

    public ArrayQueue2(int maxSize) {
        this.maxSize = maxSize;
        this.arr = new int[maxSize];
    }

    public boolean isFull(){
        return (rear+1) % maxSize == front;
    }

    public boolean isEmpty(){
        return rear == front;
    }

    public void add(int n){
        if (isFull()){
            System.out.println("队列已满!");
            return;
        }
        arr[rear] = n;
        rear = (rear+1) % maxSize;
    }

    public int get(){
        if (isEmpty()){
            throw new RuntimeException("队列为空!");
        }
        int value = arr[front];
        front = (front + 1) % maxSize;
        return value;
    }

    public int showHead(){
        if (isEmpty()){
            throw new RuntimeException("队列为空");
        }
        return arr[front];
    }
    public void show(){
        if (isEmpty()){
            System.out.println("队列为空...");
            return;
        }
        for (int i = front; i < front + size();i++){
            System.out.println(arr[i % maxSize]);
        }
    }

    public int size(){
        return (rear+maxSize-front) % maxSize;
    }

}