循环队列:大小加倍时数组值消失

时间:2019-03-22 18:32:48

标签: java data-structures queue

我的循环队列实现有一个问题,当我在resize()方法中将数组的大小加倍时。一些值消失了。

我相信dequeue()方法与此无关。 我怀疑enqueue()方法或打印方法有问题。 我在网上检查了一些答案,但找不到任何答案。由于无法找到问题,我们将不胜感激

CircularArrayQueue.java


public class CircularArrayQueue {
    private final int CAPACITY = 10;
    private int[] data;         
    private int front = 0;      
    private int size = 0;       


    public CircularArrayQueue() {
        data = new int[CAPACITY];
    }

    public CircularArrayQueue(int capacity) {
        data = new int[capacity];
    }

    public void enqueue(int element) {
        if (size == data.length) {
            resize();
        }
        data[(front + size) % data.length] = element;
        size++;
    }

    public void resize() {
        int[] temp = data;
        int currentLength = data.length;
        data = new int[2*currentLength];
        System.arraycopy(temp, 0, data, 0, currentLength);
    }

    public int dequeue() {
        if (size == 0) 
            return Integer.MIN_VALUE;

        int temp = data[front];
        data[front] = 0;
        front = (front + 1) % data.length;
        size--;
        return temp;
    }

    public int peek() {
        if (size == 0) 
            return Integer.MIN_VALUE;

        return data[front];
    }

    public int getSize() {
        return size;
    }

    public boolean isEmpty() {
        return size==0;
    }

    public void printQueue() {
        if(size == 0) {
            System.out.println("Queue is EMPTY!");
        }else {
            System.out.print("Queue: ");
            for(int i = 0; i < size; i++) {
                System.out.print(data[(i+front)%data.length]+" ");
            }
            System.out.println("");
        }
    }

    public void printArray() {
        System.out.print("Array: ");
        for(int i : data) {
            System.out.print(i+" ");
        }
        System.out.println("");
    }
}

MainCircularArrayQueue.java

public class MainCircularArrayQueue {

    public static void main(String[] args) {
        CircularArrayQueue queue = new CircularArrayQueue(3);
        System.out.println("Add 3 elements");
        queue.enqueue(11);
        queue.enqueue(22);
        queue.enqueue(33);
        queue.printQueue();
        queue.printArray();
        System.out.println();

        System.out.println("Remove 1 element");
        System.out.println("Remove: " + queue.dequeue());
        queue.printQueue();
        queue.printArray();
        System.out.println();

        System.out.println("Add 1 more element");
        queue.enqueue(44);
        queue.printQueue();
        queue.printArray();
        System.out.println();

        System.out.println("Add 1 more element");
        queue.enqueue(55);
        queue.printQueue();
        queue.printArray();
        System.out.println();

        System.out.println("Remove 1 element");
        System.out.println("Remove: " + queue.dequeue());
        queue.printQueue();
        queue.printArray();
        System.out.println();

        System.out.println("Add 4 more elements");
        queue.enqueue(66);
        queue.enqueue(77);
        queue.enqueue(88);
        queue.enqueue(99);
        queue.printQueue();
        queue.printArray();
    }
}

预期结果

Add 3 elements
Queue: 11 22 33 
Array: 11 22 33 

Remove 1 element
Remove: 11
Queue: 22 33 
Array: 0 22 33 

Add 1 more element
Queue: 22 33 44 
Array: 44 22 33 

Add 1 more element
Queue: 22 33 44 55 
Array: 22 33 44 55 0 0 

Remove 1 element
Remove: 22
Queue: 33 44 55 
Array: 0 33 44 55 0 0 

Add 4 more elements
Queue: 33 44 55 66 77 88 99 
Array: 33 44 55 66 77 88 99 0 0 0 0 0 

实际输出:

Add 3 elements
Queue: 11 22 33
Array: 11 22 33

Remove 1 element
Remove: 11
Queue: 22 33
Array: 0 22 33

Add 1 more element
Queue: 22 33 44
Array: 44 22 33

Add 1 more element
Queue: 22 33 0 55
Array: 44 22 33 0 55 0

Remove 1 element
Remove: 22
Queue: 33 0 55
Array: 44 0 33 0 55 0

Add 4 more elements
Queue: 33 0 55 66 0 0 99
Array: 77 88 33 0 55 66 0 0 99 0 0 0

2 个答案:

答案 0 :(得分:0)

您还需要跟踪rear

class CircularArrayQueue {
    private final int CAPACITY = 10;
    private int[] data;         
    private int front = 0;   
    private int rear = 0;
    private int size = 0;       


    public CircularArrayQueue() {
        data = new int[CAPACITY];
    }

    public CircularArrayQueue(int capacity) {
        data = new int[capacity];
    }

    public void enqueue(int element) {
        if (size == data.length) {
            resize();
        }
        data[rear] = element;
        rear = (rear + 1) % data.length;
        size++;
    }

    public void resize() {
        int[] temp = data;
        int currentLength = data.length;
        data = new int[2*currentLength];

        for (int i = 0; i < currentLength; i++) {
            data[i] = temp[(i + front) % currentLength];
        }

        front = 0;
        rear = currentLength;
    }

    public int dequeue() {
        if (size == 0) 
            return Integer.MIN_VALUE;

        int temp = data[front];
        data[front] = 0;
        front = (front + 1) % data.length;
        size--;
        return temp;
    }

    public int peek() {
        if (size == 0) 
            return Integer.MIN_VALUE;

        return data[front];
    }

    public int getSize() {
        return size;
    }

    public boolean isEmpty() {
        return size==0;
    }

    public void printQueue() {
        if(size == 0) {
            System.out.println("Queue is EMPTY!");
        }else {
            System.out.print("Queue: ");
            for(int i = 0; i < size; i++) {
                System.out.print(data[(i+front)%data.length]+" ");
            }
            System.out.println("");
        }
    }

    public void printArray() {
        System.out.print("Array: ");
        for(int i : data) {
            System.out.print(i+" ");
        }
        System.out.println("");
    }
}

答案 1 :(得分:0)

问题不一定是enqueue()dequeue()。发生的事情是,当缓冲区自动调整大小时,它将更改队列中元素的顺序。 当数组为[44 22 33]时,front在索引1处,并且“后位置”被定义为在其前面的size个索引,也环绕在索引1处。添加下一个数字会触发要调整大小的数组,从而形成[44 22 33 0 0 0]55被添加到索引4,因为“后位置”计算不再环绕数组的末尾。 Mokarrom Hossain的上面的代码示例应该可以工作,因为他修改了resize()以便按排队顺序将数字从原始数组复制到调整大小的数组。