基于动态数组设计循环队列

基于动态数组设计循环队列

题目

(1)设计你的循环队列实现。 循环队列是一种线性数据结构,其操作表现基于 FIFO(先进先出)原则并且队尾被连接在队首之后以形成一个循环。它也被称为“环形缓冲器”。

(2)循环队列的一个好处是我们可以利用这个队列之前用过的空间。在一个普通队列里,一旦一个队列满了,我们就不能插入下一个元素,即使在队列前面仍有空间(假溢出)。但是使用循环队列,我们能使用这些空间去存储新的值。

(3)你的实现应该支持如下操作:

  • MyCircularQueue(k): 构造器,设置队列长度为 k 。
  • Front: 从队首获取元素。如果队列为空,返回 -1 。
  • Rear: 获取队尾元素。如果队列为空,返回 -1 。
  • enQueue(value): 向循环队列插入一个元素。如果成功插入则返回真。
  • deQueue(): 从循环队列中删除一个元素。如果成功删除则返回真。
  • isEmpty(): 检查循环队列是否为空。
  • isFull(): 检查循环队列是否已满。

(4)示例如下:
MyCircularQueue circularQueue = new MyCircularQueue(3); // 设置长度为 3
circularQueue.enQueue(1); // 返回 true
circularQueue.enQueue(2); // 返回 true
circularQueue.enQueue(3); // 返回 true
circularQueue.enQueue(4); // 返回 false,队列已满
circularQueue.Rear(); // 返回 3
circularQueue.isFull(); // 返回 true
circularQueue.deQueue(); // 返回 true
circularQueue.enQueue(4); // 返回 true
circularQueue.Rear(); // 返回 4

解决思路

  • 使用数组实现队列的功能。
  • 定义head指向第一个元素,定义tail指向最后一个元素的下一个位置,定义cnt记录队列中的元素个数。

代码

  • C++代码
# include <stdio.h>
#include <vector>

using namespace std;


class MyCircularQueue{
public:
    vector<int> arr;    // 创建一个动态数组,使用数组实现队列。
    int head;           // 指向队列的首位。
    int tail;           // 指向最后一个元素的下一个位置。
    int cnt;            // 记录队列中元素的个数。

    MyCircularQueue(int k): arr(k), head(0), tail(0), cnt(0) {}

    // 入队
    bool enQueue(int value) {
        if (isFull()) {
            return false;
        }
        arr[tail] = value;
        tail = (tail + 1) % arr.size();
        cnt += 1;
        return true;
    }

    // 出队
    bool deQueue() {
        if (isEmpty()) {
            return false;
        }
        head = (head + 1) % arr.size();
        cnt -= 1;
        return true;
    }

    // 判断队列是否为空
    bool isEmpty() {
        return 0 == cnt;
    }

    // 判断队列是否已满
    bool isFull() {
        return arr.size() == cnt;
    }

    // 获取队首元素
    int Front() {
        if (isEmpty()) {
            return -1;
        }
        return arr[head];
    }

    // 获取队尾元素
    int Rear() {
        if (isEmpty()) {
            return -1;
        }
        // tail-1对应的元素才是最后一个元素。
        // tail - 1 + arr.size()是为了防止tail=0时,tai-1成为负数,导致访问越界。
        return arr[(tail - 1 + arr.size()) % arr.size()];
    }
};


int main() {
    int k = 3;      // 设置长度为 3
    MyCircularQueue *circularQueue = new MyCircularQueue(k);
    printf("%d\n", circularQueue->enQueue(1));      // 返回 true
    printf("%d\n", circularQueue->enQueue(2));      // 返回 true
    printf("%d\n", circularQueue->enQueue(3));      // 返回 true
    printf("%d\n", circularQueue->enQueue(4));      // 返回 false,队列已满

    printf("%d\n", circularQueue->Rear());          // 返回 3
    printf("%d\n", circularQueue->isFull());        // 返回 true
    printf("%d\n", circularQueue->deQueue());       // 返回 true
    printf("%d\n", circularQueue->enQueue(4));      // 返回 true
    printf("%d\n", circularQueue->Rear());          // 返回 4

    return 0;
}
  • python代码
# -*- coding: utf-8 -*-

class MyCircularQueue:
    def __init__(self, k: int):
        self.arr = [-1 for i in range(k)]       # 创建一个list实现队列。
        self.size = k       # 记录队列的大小。
        self.head = 0       # 指向队列的首位。
        self.tail = 0       # 指向最后一个元素的下一个位置。
        self.cnt = 0        # 记录队列中元素的个数。

    # 入队
    def enQueue(self, value: int):
        if self.isFull():
            return False

        self.arr[self.tail] = value
        self.tail = (self.tail + 1) % self.size
        self.cnt += 1
        return True

    # 出队
    def deQueue(self):
        if self.isEmpty():
            return False
        self.head = (self.head + 1) % self.size
        self.cnt -= 1
        return True

    # 获取队首元素
    def Front(self):
        if self.isEmpty():
            return -1
        return self.arr[self.head]

    # 获取队尾元素
    def Rear(self):
        if self.isEmpty():
            return -1
        # tail - 1对应的元素才是最后一个元素。
        # tail - 1 + self.size()是为了防止tail = 0时,tai - 1成为负数,导致访问越界。
        return self.arr[(self.tail - 1 + self.size) % self.size]

    # 判断队列是否为空
    def isEmpty(self):
        return 0 == self.cnt

    # 判断队列是否已满
    def isFull(self):
        return self.cnt == self.size


def main():
    k: int = 3
    circularQueue: MyCircularQueue = MyCircularQueue(k)
    print(circularQueue.enQueue(1))     # 返回 true
    print(circularQueue.enQueue(2))     # 返回 true
    print(circularQueue.enQueue(3))     # 返回 true
    print(circularQueue.enQueue(4))     # 返回 false,队列已满

    print(circularQueue.Rear())         # 返回 3
    print(circularQueue.isFull())       # 返回 true
    print(circularQueue.deQueue())      # 返回 true
    print(circularQueue.enQueue(4))     # 返回 true
    print(circularQueue.Rear())         # 返回 4


if __name__ == "__main__":
    main()

说明

  • 对应LeetCode第622题。
  • 链接:https://leetcode-cn.com/problems/design-circular-queue/
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值