Fix array queue.

This commit is contained in:
Yudong Jin 2023-02-01 03:23:29 +08:00
parent 658ad90377
commit 5eae708035
15 changed files with 425 additions and 365 deletions

8
codes/c/.gitignore vendored Normal file
View file

@ -0,0 +1,8 @@
# Ignore all
*
# Unignore all with extensions
!*.*
# Unignore all dirs
!*/
*.dSYM/

View file

@ -9,9 +9,9 @@
/* 基于环形数组形成的队列 */ /* 基于环形数组形成的队列 */
struct ArrayQueue { struct ArrayQueue {
int *nums; // 用于存储队列元素的数组 int *nums; // 用于存储队列元素的数组
int cap; // 队列容量 int front; // 队首指针,指向队首元素
int front; // 头指针,指向队首 int queSize; // 尾指针,指向队尾 + 1
int rear; // 尾指针,指向队尾 + 1 int queCapacity; // 队列容量
}; };
typedef struct ArrayQueue ArrayQueue; typedef struct ArrayQueue ArrayQueue;
@ -20,33 +20,31 @@ typedef struct ArrayQueue ArrayQueue;
ArrayQueue *newArrayQueue(int capacity) { ArrayQueue *newArrayQueue(int capacity) {
ArrayQueue *queue = (ArrayQueue *) malloc(sizeof(ArrayQueue)); ArrayQueue *queue = (ArrayQueue *) malloc(sizeof(ArrayQueue));
// 初始化数组 // 初始化数组
queue->cap = capacity; queue->queCapacity = capacity;
queue->nums = (int *) malloc(sizeof(int) * queue->cap); queue->nums = (int *) malloc(sizeof(int) * queue->queCapacity);
queue->front = 0; queue->front = queue->queSize = 0;
queue->rear = 0;
return queue; return queue;
} }
/* 析构函数 */ /* 析构函数 */
void delArrayQueue(ArrayQueue *queue) { void delArrayQueue(ArrayQueue *queue) {
free(queue->nums); free(queue->nums);
queue->cap = 0; queue->queCapacity = 0;
} }
/* 获取队列的容量 */ /* 获取队列的容量 */
int capacity(ArrayQueue *queue) { int capacity(ArrayQueue *queue) {
return queue->cap; return queue->queCapacity;
} }
/* 获取队列的长度 */ /* 获取队列的长度 */
int size(ArrayQueue *queue) { int size(ArrayQueue *queue) {
// 由于将数组看作环形队列,可能 rear < front因此需要取余数 return queue->queSize;
return (capacity(queue) + queue->rear - queue->front) % capacity(queue);
} }
/* 判断队列是否为空 */ /* 判断队列是否为空 */
bool empty(ArrayQueue *queue) { bool empty(ArrayQueue *queue) {
return queue->rear - queue->front == 0; return queue->queSize == 0;
} }
/* 访问队首元素 */ /* 访问队首元素 */
@ -61,26 +59,30 @@ void offer(ArrayQueue *queue, int num) {
printf("队列已满\r\n"); printf("队列已满\r\n");
return; return;
} }
queue->nums[queue->rear] = num; // 计算队尾指针,指向队尾索引 + 1
queue->rear = (queue->rear + 1) % capacity(queue); // 通过取余操作,实现 rear 越过数组尾部后回到头部
int rear = (queue->front + queue->queSize) % queue->queCapacity;
// 尾结点后添加 num
queue->nums[rear] = num;
queue->queSize++;
} }
/* 出队 */ /* 出队 */
void poll(ArrayQueue *queue) { void poll(ArrayQueue *queue) {
int num = peek(queue); int num = peek(queue);
queue->front = (queue->front + 1) % capacity(queue); // 队首指针向后移动一位,若越过尾部则返回到数组头部
queue->front = (queue->front + 1) % queue->queCapacity;
queue->queSize--;
} }
/* 打印基于环形数组形成的队列 */ /* 打印基于环形数组形成的队列 */
void printArrayQueue(ArrayQueue *queue) { void printArrayQueue(ArrayQueue *queue) {
int siz = size(queue); int arr[queue->queSize];
int cap = capacity(queue);
int arr[siz];
// 拷贝 // 拷贝
for (int i = 0, j = queue->front; i < siz; i++, j++) { for (int i = 0, j = queue->front; i < queue->queSize; i++, j++) {
arr[i] = queue->nums[j % cap]; arr[i] = queue->nums[j % queue->queCapacity];
} }
printArray(arr, siz); printArray(arr, queue->queSize);
} }

View file

@ -10,15 +10,16 @@
class ArrayQueue { class ArrayQueue {
private: private:
int *nums; // 用于存储队列元素的数组 int *nums; // 用于存储队列元素的数组
int cap; // 队列容量 int front; // 队首指针,指向队首元素
int front = 0; // 头指针,指向队首 int queSize; // 队列长度
int rear = 0; // 尾指针,指向队尾 + 1 int queCapacity; // 队列容量
public: public:
ArrayQueue(int capacity) { ArrayQueue(int capacity) {
// 初始化数组 // 初始化数组
cap = capacity;
nums = new int[capacity]; nums = new int[capacity];
queCapacity = capacity;
front = queSize = 0;
} }
~ArrayQueue() { ~ArrayQueue() {
@ -27,37 +28,39 @@ public:
/* 获取队列的容量 */ /* 获取队列的容量 */
int capacity() { int capacity() {
return cap; return queCapacity;
} }
/* 获取队列的长度 */ /* 获取队列的长度 */
int size() { int size() {
// 由于将数组看作为环形,可能 rear < front ,因此需要取余数 return queSize;
return (capacity() + rear - front) % capacity();
} }
/* 判断队列是否为空 */ /* 判断队列是否为空 */
bool empty() { bool empty() {
return rear - front == 0; return size() == 0;
} }
/* 入队 */ /* 入队 */
void offer(int num) { void offer(int num) {
if (size() == capacity()) { if (queSize == queCapacity) {
cout << "队列已满" << endl; cout << "队列已满" << endl;
return; return;
} }
// 计算队尾指针,指向队尾索引 + 1
// 通过取余操作,实现 rear 越过数组尾部后回到头部
int rear = (front + queSize) % queCapacity;
// 尾结点后添加 num // 尾结点后添加 num
nums[rear] = num; nums[rear] = num;
// 尾指针向后移动一位,越过尾部后返回到数组头部 queSize++;
rear = (rear + 1) % capacity();
} }
/* 出队 */ /* 出队 */
void poll() { void poll() {
int num = peek(); int num = peek();
// 队头指针向后移动一位,若越过尾部则返回到数组头部 // 队首指针向后移动一位,若越过尾部则返回到数组头部
front = (front + 1) % capacity(); front = (front + 1) % queCapacity;
queSize--;
} }
/* 访问队首元素 */ /* 访问队首元素 */
@ -69,11 +72,10 @@ public:
/* 将数组转化为 Vector 并返回 */ /* 将数组转化为 Vector 并返回 */
vector<int> toVector() { vector<int> toVector() {
int siz = size(); int cap = queCapacity;
int cap = capacity();
// 仅转换有效长度范围内的列表元素 // 仅转换有效长度范围内的列表元素
vector<int> arr(siz); vector<int> arr(queSize);
for (int i = 0, j = front; i < siz; i++, j++) { for (int i = 0, j = front; i < queSize; i++, j++) {
arr[i] = nums[j % cap]; arr[i] = nums[j % cap];
} }
return arr; return arr;

View file

@ -13,13 +13,13 @@ namespace hello_algo.chapter_stack_and_queue
class ArrayQueue class ArrayQueue
{ {
private int[] nums; // 用于存储队列元素的数组 private int[] nums; // 用于存储队列元素的数组
private int front = 0; // 头指针指向队首 private int front; // 队首指针指向队首元素
private int rear = 0; // 尾指针指向队尾 + 1 private int queSize; // 队列长度
public ArrayQueue(int capacity) public ArrayQueue(int capacity)
{ {
// 初始化数组
nums = new int[capacity]; nums = new int[capacity];
front = queSize = 0;
} }
/* 获取队列的容量 */ /* 获取队列的容量 */
@ -31,37 +31,38 @@ namespace hello_algo.chapter_stack_and_queue
/* 获取队列的长度 */ /* 获取队列的长度 */
public int size() public int size()
{ {
int capacity = this.capacity(); return queSize;
// 由于将数组看作为环形可能 rear < front 因此需要取余数
return (capacity + rear - front) % capacity;
} }
/* 判断队列是否为空 */ /* 判断队列是否为空 */
public bool isEmpty() public bool isEmpty()
{ {
return rear - front == 0; return queSize == 0;
} }
/* 入队 */ /* 入队 */
public void offer(int num) public void offer(int num)
{ {
if (size() == capacity()) if (queSize == capacity())
{ {
Console.WriteLine("队列已满"); Console.WriteLine("队列已满");
return; return;
} }
// 计算尾指针指向队尾索引 + 1
// 通过取余操作实现 rear 越过数组尾部后回到头部
int rear = (front + queSize) % capacity();
// 尾结点后添加 num // 尾结点后添加 num
nums[rear] = num; nums[rear] = num;
// 尾指针向后移动一位越过尾部后返回到数组头部 queSize++;
rear = (rear + 1) % capacity();
} }
/* 出队 */ /* 出队 */
public int poll() public int poll()
{ {
int num = peek(); int num = peek();
// 指针向后移动一位若越过尾部则返回到数组头部 // 指针向后移动一位若越过尾部则返回到数组头部
front = (front + 1) % capacity(); front = (front + 1) % capacity();
queSize--;
return num; return num;
} }
@ -76,13 +77,11 @@ namespace hello_algo.chapter_stack_and_queue
/* 返回数组 */ /* 返回数组 */
public int[] toArray() public int[] toArray()
{ {
int size = this.size();
int capacity = this.capacity();
// 仅转换有效长度范围内的列表元素 // 仅转换有效长度范围内的列表元素
int[] res = new int[size]; int[] res = new int[queSize];
for (int i = 0, j = front; i < size; i++, j++) for (int i = 0, j = front; i < queSize; i++, j++)
{ {
res[i] = nums[j % capacity]; res[i] = nums[j % this.capacity()];
} }
return res; return res;
} }

View file

@ -6,54 +6,53 @@ package chapter_stack_and_queue
/* 基于环形数组实现的队列 */ /* 基于环形数组实现的队列 */
type arrayQueue struct { type arrayQueue struct {
data []int // 用于存储队列元素的数组 nums []int // 用于存储队列元素的数组
capacity int // 队列容量(即最多容量的元素个数) front int // 队首指针,指向队首元素
front int // 头指针,指向队首 queSize int // 队列长度
rear int // 尾指针,指向队尾 + 1 queCapacity int // 队列容量(即最大容纳元素数量)
} }
// newArrayQueue 基于环形数组实现的队列 // newArrayQueue 基于环形数组实现的队列
func newArrayQueue(capacity int) *arrayQueue { func newArrayQueue(queCapacity int) *arrayQueue {
return &arrayQueue{ return &arrayQueue{
data: make([]int, capacity), nums: make([]int, queCapacity),
capacity: capacity, queCapacity: queCapacity,
front: 0, front: 0,
rear: 0, queSize: 0,
} }
} }
// size 获取队列的长度 // size 获取队列的长度
func (q *arrayQueue) size() int { func (q *arrayQueue) size() int {
size := (q.capacity + q.rear - q.front) % q.capacity return q.queSize
return size
} }
// isEmpty 判断队列是否为空 // isEmpty 判断队列是否为空
func (q *arrayQueue) isEmpty() bool { func (q *arrayQueue) isEmpty() bool {
return q.rear-q.front == 0 return q.queSize == 0
} }
// offer 入队 // offer 入队
func (q *arrayQueue) offer(v int) { func (q *arrayQueue) offer(num int) {
// 当 rear == capacity 表示队列已满 // 当 rear == queCapacity 表示队列已满
if q.size() == q.capacity { if q.queSize == q.queCapacity {
return return
} }
// 尾结点后添加 // 计算尾指针,指向队尾索引 + 1
q.data[q.rear] = v // 通过取余操作,实现 rear 越过数组尾部后回到头部
// 尾指针向后移动一位,越过尾部后返回到数组头部 rear := (q.front + q.queSize) % q.queCapacity
q.rear = (q.rear + 1) % q.capacity // 尾结点后添加 num
q.nums[rear] = num
q.queSize++
} }
// poll 出队 // poll 出队
func (q *arrayQueue) poll() any { func (q *arrayQueue) poll() any {
if q.isEmpty() { num := q.peek()
return nil // 队首指针向后移动一位,若越过尾部则返回到数组头部
} q.front = (q.front + 1) % q.queCapacity
v := q.data[q.front] q.queSize--
// 队头指针向后移动一位,若越过尾部则返回到数组头部 return num
q.front = (q.front + 1) % q.capacity
return v
} }
// peek 访问队首元素 // peek 访问队首元素
@ -61,11 +60,15 @@ func (q *arrayQueue) peek() any {
if q.isEmpty() { if q.isEmpty() {
return nil return nil
} }
v := q.data[q.front] return q.nums[q.front]
return v
} }
// 获取 Slice 用于打印 // 获取 Slice 用于打印
func (q *arrayQueue) toSlice() []int { func (q *arrayQueue) toSlice() []int {
return q.data[q.front:q.rear] rear := (q.front + q.queSize)
if rear >= q.queCapacity {
rear %= q.queCapacity
return append(q.nums[q.front:], q.nums[:rear]...)
}
return q.nums[q.front:rear]
} }

View file

@ -75,6 +75,14 @@ func TestArrayQueue(t *testing.T) {
// 判断是否为空 // 判断是否为空
isEmpty := queue.isEmpty() isEmpty := queue.isEmpty()
fmt.Println("队是否为空 =", isEmpty) fmt.Println("队是否为空 =", isEmpty)
/* 测试环形数组 */
for i := 0; i < 10; i++ {
queue.offer(i)
queue.poll()
fmt.Print("第", i, "轮入队 + 出队后 queue =")
PrintSlice(queue.toSlice())
}
} }
func TestLinkedListQueue(t *testing.T) { func TestLinkedListQueue(t *testing.T) {

View file

@ -11,12 +11,12 @@ import java.util.*;
/* 基于环形数组实现的队列 */ /* 基于环形数组实现的队列 */
class ArrayQueue { class ArrayQueue {
private int[] nums; // 用于存储队列元素的数组 private int[] nums; // 用于存储队列元素的数组
private int front = 0; // 头指针指向队首 private int front; // 队首指针指向队首元素
private int rear = 0; // 尾指针指向队尾 + 1 private int queSize; // 队列长度
public ArrayQueue(int capacity) { public ArrayQueue(int capacity) {
// 初始化数组
nums = new int[capacity]; nums = new int[capacity];
front = queSize = 0;
} }
/* 获取队列的容量 */ /* 获取队列的容量 */
@ -26,33 +26,34 @@ class ArrayQueue {
/* 获取队列的长度 */ /* 获取队列的长度 */
public int size() { public int size() {
int capacity = capacity(); return queSize;
// 由于将数组看作为环形可能 rear < front 因此需要取余数
return (capacity + rear - front) % capacity;
} }
/* 判断队列是否为空 */ /* 判断队列是否为空 */
public boolean isEmpty() { public boolean isEmpty() {
return rear - front == 0; return queSize == 0;
} }
/* 入队 */ /* 入队 */
public void offer(int num) { public void offer(int num) {
if (size() == capacity()) { if (queSize == capacity()) {
System.out.println("队列已满"); System.out.println("队列已满");
return; return;
} }
// 计算尾指针指向队尾索引 + 1
// 通过取余操作实现 rear 越过数组尾部后回到头部
int rear = (front + queSize) % capacity();
// 尾结点后添加 num // 尾结点后添加 num
nums[rear] = num; nums[rear] = num;
// 尾指针向后移动一位越过尾部后返回到数组头部 queSize++;
rear = (rear + 1) % capacity();
} }
/* 出队 */ /* 出队 */
public int poll() { public int poll() {
int num = peek(); int num = peek();
// 指针向后移动一位若越过尾部则返回到数组头部 // 指针向后移动一位若越过尾部则返回到数组头部
front = (front + 1) % capacity(); front = (front + 1) % capacity();
queSize--;
return num; return num;
} }
@ -65,12 +66,10 @@ class ArrayQueue {
/* 返回数组 */ /* 返回数组 */
public int[] toArray() { public int[] toArray() {
int size = size();
int capacity = capacity();
// 仅转换有效长度范围内的列表元素 // 仅转换有效长度范围内的列表元素
int[] res = new int[size]; int[] res = new int[queSize];
for (int i = 0, j = front; i < size; i++, j++) { for (int i = 0, j = front; i < queSize; i++, j++) {
res[i] = nums[j % capacity]; res[i] = nums[j % capacity()];
} }
return res; return res;
} }

View file

@ -4,48 +4,49 @@
* Author: S-N-O-R-L-A-X (snorlax.xu@outlook.com) * Author: S-N-O-R-L-A-X (snorlax.xu@outlook.com)
*/ */
/* 基于环形数组实现的队列 */ /* 基于环形数组实现的队列 */
class ArrayQueue { class ArrayQueue {
#queue; // 用于存储队列元素的数组 #nums; // 用于存储队列元素的数组
#front = 0; // 头指针,指向队首 #front = 0; // 队首指针,指向队首元素
#rear = 0; // 尾指针,指向队尾 + 1 #queSize = 0; // 队列长度
constructor(capacity) { constructor(capacity) {
this.#queue = new Array(capacity); this.#nums = new Array(capacity);
} }
/* 获取队列的容量 */ /* 获取队列的容量 */
get capacity() { get capacity() {
return this.#queue.length; return this.#nums.length;
} }
/* 获取队列的长度 */ /* 获取队列的长度 */
get size() { get size() {
// 由于将数组看作为环形,可能 rear < front ,因此需要取余数 return this.#queSize;
return (this.capacity + this.#rear - this.#front) % this.capacity;
} }
/* 判断队列是否为空 */ /* 判断队列是否为空 */
empty() { empty() {
return this.#rear - this.#front == 0; return this.#queSize == 0;
} }
/* 入队 */ /* 入队 */
offer(num) { offer(num) {
if (this.size == this.capacity) if (this.size == this.capacity)
throw new Error("队列已满"); throw new Error("队列已满");
// 计算尾指针,指向队尾索引 + 1
// 通过取余操作,实现 rear 越过数组尾部后回到头部
const rear = (this.#front + this.size) % this.capacity;
// 尾结点后添加 num // 尾结点后添加 num
this.#queue[this.#rear] = num; this.#nums[rear] = num;
// 尾指针向后移动一位,越过尾部后返回到数组头部 this.#queSize++;
this.#rear = (this.#rear + 1) % this.capacity;
} }
/* 出队 */ /* 出队 */
poll() { poll() {
const num = this.peek(); const num = this.peek();
// 队指针向后移动一位,若越过尾部则返回到数组头部 // 队指针向后移动一位,若越过尾部则返回到数组头部
this.#front = (this.#front + 1) % this.capacity; this.#front = (this.#front + 1) % this.capacity;
this.#queSize--;
return num; return num;
} }
@ -53,17 +54,15 @@ class ArrayQueue {
peek() { peek() {
if (this.empty()) if (this.empty())
throw new Error("队列为空"); throw new Error("队列为空");
return this.#queue[this.#front]; return this.#nums[this.#front];
} }
/* 返回 Array */ /* 返回 Array */
toArray() { toArray() {
const siz = this.size;
const cap = this.capacity;
// 仅转换有效长度范围内的列表元素 // 仅转换有效长度范围内的列表元素
const arr = new Array(siz); const arr = new Array(this.size);
for (let i = 0, j = this.#front; i < siz; i++, j++) { for (let i = 0, j = this.#front; i < this.size; i++, j++) {
arr[i] = this.#queue[j % cap]; arr[i] = this.#nums[j % this.capacity];
} }
return arr; return arr;
} }
@ -81,8 +80,7 @@ queue.offer(3);
queue.offer(2); queue.offer(2);
queue.offer(5); queue.offer(5);
queue.offer(4); queue.offer(4);
console.log("队列 queue = "); console.log("队列 queue =", queue.toArray());
console.log(queue.toArray());
/* 访问队首元素 */ /* 访问队首元素 */
const peek = queue.peek(); const peek = queue.peek();
@ -90,8 +88,7 @@ console.log("队首元素 peek = " + peek);
/* 元素出队 */ /* 元素出队 */
const poll = queue.poll(); const poll = queue.poll();
console.log("出队元素 poll = " + poll + ",出队后 queue = "); console.log("出队元素 poll = " + poll + ",出队后 queue =", queue.toArray());
console.log(queue.toArray());
/* 获取队列的长度 */ /* 获取队列的长度 */
const size = queue.size; const size = queue.size;
@ -105,6 +102,5 @@ console.log("队列是否为空 = " + empty);
for (let i = 0; i < 10; i++) { for (let i = 0; i < 10; i++) {
queue.offer(i); queue.offer(i);
queue.poll(); queue.poll();
console.log("第 " + i + " 轮入队 + 出队后 queue = "); console.log("第 " + i + " 轮入队 + 出队后 queue =", queue.toArray());
console.log(queue.toArray());
} }

View file

@ -4,11 +4,6 @@
* Author: IsChristina (christinaxia77@foxmail.com) * Author: IsChristina (christinaxia77@foxmail.com)
*/ */
function Trunk(prev, str) {
this.prev = prev;
this.str = str;
}
/** /**
* Print a linked list * Print a linked list
* @param head * @param head
@ -22,6 +17,11 @@ function printLinkedList(head) {
console.log(list.join(" -> ")); console.log(list.join(" -> "));
} }
function Trunk(prev, str) {
this.prev = prev;
this.str = str;
}
/** /**
* The interface of the tree printer * The interface of the tree printer
* This tree printer is borrowed from TECHIE DELIGHT * This tree printer is borrowed from TECHIE DELIGHT
@ -83,6 +83,6 @@ function showTrunks(p) {
} }
module.exports = { module.exports = {
printTree,
printLinkedList, printLinkedList,
printTree
} }

View file

@ -14,8 +14,8 @@ from include import *
class ArrayQueue: class ArrayQueue:
def __init__(self, size): def __init__(self, size):
self.__nums = [0] * size # 用于存储队列元素的数组 self.__nums = [0] * size # 用于存储队列元素的数组
self.__front = 0 # 头指针,指向队首 self.__front = 0 # 队首指针,指向队首元素
self.__rear = 0 # 尾指针,指向队尾 + 1 self.__size = 0 # 队列长度
""" 获取队列的容量 """ """ 获取队列的容量 """
def capacity(self): def capacity(self):
@ -23,35 +23,33 @@ class ArrayQueue:
""" 获取队列的长度 """ """ 获取队列的长度 """
def size(self): def size(self):
# 由于将数组看作为环形,可能 rear < front ,因此需要取余数 return self.__size
return (self.capacity() + self.__rear - self.__front) % self.capacity()
""" 判断队列是否为空 """ """ 判断队列是否为空 """
def is_empty(self): def is_empty(self):
return (self.__rear - self.__front) == 0 return self.__size == 0
""" 入队 """ """ 入队 """
def push(self, val): def push(self, num):
if self.size() == self.capacity(): assert self.__size < self.capacity(), "队列已满"
print("队列已满") # 计算尾指针,指向队尾索引 + 1
return False # 通过取余操作,实现 rear 越过数组尾部后回到头部
rear = (self.__front + self.__size) % self.capacity()
# 尾结点后添加 num # 尾结点后添加 num
self.__nums[self.__rear] = val self.__nums[rear] = num
# 尾指针向后移动一位,越过尾部后返回到数组头部 self.__size += 1
self.__rear = (self.__rear + 1) % self.capacity()
""" 出队 """ """ 出队 """
def poll(self): def poll(self):
num = self.peek() num = self.peek()
# 队指针向后移动一位,若越过尾部则返回到数组头部 # 队指针向后移动一位,若越过尾部则返回到数组头部
self.__front = (self.__front + 1) % self.capacity() self.__front = (self.__front + 1) % self.capacity()
self.__size -= 1
return num return num
""" 访问队首元素 """ """ 访问队首元素 """
def peek(self): def peek(self):
if self.is_empty(): assert not self.is_empty(), "队列为空"
print("队列为空")
return False
return self.__nums[self.__front] return self.__nums[self.__front]
""" 返回列表用于打印 """ """ 返回列表用于打印 """
@ -93,3 +91,9 @@ if __name__ == "__main__":
""" 判断队列是否为空 """ """ 判断队列是否为空 """
is_empty = queue.is_empty() is_empty = queue.is_empty()
print("队列是否为空 =", is_empty) print("队列是否为空 =", is_empty)
""" 测试环形数组 """
for i in range(10):
queue.push(i);
queue.poll();
print("", i, "轮入队 + 出队后 queue = ", queue.to_list());

View file

@ -7,8 +7,8 @@
/* */ /* */
class ArrayQueue { class ArrayQueue {
private var nums: [Int] // private var nums: [Int] //
private var front = 0 // private var front = 0 //
private var rear = 0 // + 1 private var queSize = 0 //
init(capacity: Int) { init(capacity: Int) {
// //
@ -22,14 +22,12 @@ class ArrayQueue {
/* */ /* */
func size() -> Int { func size() -> Int {
let capacity = capacity() queSize
// rear < front
return (capacity + rear - front) % capacity
} }
/* */ /* */
func isEmpty() -> Bool { func isEmpty() -> Bool {
rear - front == 0 queSize == 0
} }
/* */ /* */
@ -38,19 +36,22 @@ class ArrayQueue {
print("队列已满") print("队列已满")
return return
} }
// + 1
// rear
int rear = (front + queSize) % capacity();
// num // num
nums[rear] = num nums[rear] = num;
// queSize++;
rear = (rear + 1) % capacity()
} }
/* */ /* */
@discardableResult @discardableResult
func poll() -> Int { func poll() -> Int {
let num = peek() let num = peek()
// //
front = (front + 1) % capacity() front = (front + 1) % capacity();
return num queSize--;
return num;
} }
/* 访 */ /* 访 */
@ -63,12 +64,10 @@ class ArrayQueue {
/* */ /* */
func toArray() -> [Int] { func toArray() -> [Int] {
let size = size()
let capacity = capacity()
// //
var res = Array(repeating: 0, count: size) var res = Array(repeating: 0, count: queSize)
for (i, j) in sequence(first: (0, front), next: { $0 < size - 1 ? ($0 + 1, $1 + 1) : nil }) { for (i, j) in sequence(first: (0, front), next: { $0 < queSize - 1 ? ($0 + 1, $1 + 1) : nil }) {
res[i] = nums[j % capacity] res[i] = nums[j % capacity()]
} }
return res return res
} }

View file

@ -4,49 +4,50 @@
* Author: S-N-O-R-L-A-X (snorlax.xu@outlook.com) * Author: S-N-O-R-L-A-X (snorlax.xu@outlook.com)
*/ */
/* 基于环形数组实现的队列 */ /* 基于环形数组实现的队列 */
class ArrayQueue { class ArrayQueue {
private queue: number[]; // 用于存储队列元素的数组 private nums: number[]; // 用于存储队列元素的数组
private front: number = 0; // 头指针,指向队首 private front: number; // 队首指针,指向队首元素
private rear: number = 0; // 尾指针,指向队尾 + 1 private queSize: number; // 队列长度
private CAPACITY: number = 1e5;
constructor(capacity?: number) { constructor(capacity: number) {
this.queue = new Array<number>(capacity ?? this.CAPACITY); this.nums = new Array<number>(capacity);
this.front = this.queSize = 0;
} }
/* 获取队列的容量 */ /* 获取队列的容量 */
get capacity(): number { get capacity(): number {
return this.queue.length; return this.nums.length;
} }
/* 获取队列的长度 */ /* 获取队列的长度 */
get size(): number { get size(): number {
// 由于将数组看作为环形,可能 rear < front ,因此需要取余数 return this.queSize;
return (this.capacity + this.rear - this.front) % this.capacity;
} }
/* 判断队列是否为空 */ /* 判断队列是否为空 */
empty(): boolean { empty(): boolean {
return this.rear - this.front == 0; return this.queSize == 0;
} }
/* 入队 */ /* 入队 */
offer(num: number): void { offer(num: number): void {
if (this.size == this.capacity) if (this.size == this.capacity)
throw new Error("队列已满"); throw new Error("队列已满");
// 计算尾指针,指向队尾索引 + 1
// 通过取余操作,实现 rear 越过数组尾部后回到头部
const rear = (this.front + this.queSize) % this.capacity;
// 尾结点后添加 num // 尾结点后添加 num
this.queue[this.rear] = num; this.nums[rear] = num;
// 尾指针向后移动一位,越过尾部后返回到数组头部 this.queSize++;
this.rear = (this.rear + 1) % this.capacity;
} }
/* 出队 */ /* 出队 */
poll(): number { poll(): number {
const num = this.peek(); const num = this.peek();
// 队指针向后移动一位,若越过尾部则返回到数组头部 // 队指针向后移动一位,若越过尾部则返回到数组头部
this.front = (this.front + 1) % this.capacity; this.front = (this.front + 1) % this.capacity;
this.queSize--;
return num; return num;
} }
@ -54,17 +55,15 @@ class ArrayQueue {
peek(): number { peek(): number {
if (this.empty()) if (this.empty())
throw new Error("队列为空"); throw new Error("队列为空");
return this.queue[this.front]; return this.nums[this.front];
} }
/* 返回 Array */ /* 返回 Array */
toArray(): number[] { toArray(): number[] {
const siz = this.size;
const cap = this.capacity;
// 仅转换有效长度范围内的列表元素 // 仅转换有效长度范围内的列表元素
const arr = new Array(siz); const arr = new Array(this.size);
for (let i = 0, j = this.front; i < siz; i++, j++) { for (let i = 0, j = this.front; i < this.size; i++, j++) {
arr[i] = this.queue[j % cap]; arr[i] = this.nums[j % this.capacity];
} }
return arr; return arr;
} }
@ -80,8 +79,7 @@ queue.offer(3);
queue.offer(2); queue.offer(2);
queue.offer(5); queue.offer(5);
queue.offer(4); queue.offer(4);
console.log("队列 queue = "); console.log("队列 queue =", queue.toArray());
console.log(queue.toArray());
/* 访问队首元素 */ /* 访问队首元素 */
const peek = queue.peek(); const peek = queue.peek();
@ -89,8 +87,7 @@ console.log("队首元素 peek = " + peek);
/* 元素出队 */ /* 元素出队 */
const poll = queue.poll(); const poll = queue.poll();
console.log("出队元素 poll = " + poll + ",出队后 queue = "); console.log("出队元素 poll = " + poll + ",出队后 queue =", queue.toArray());
console.log(queue.toArray());
/* 获取队列的长度 */ /* 获取队列的长度 */
const size = queue.size; const size = queue.size;
@ -104,7 +101,7 @@ console.log("队列是否为空 = " + empty);
for (let i = 0; i < 10; i++) { for (let i = 0; i < 10; i++) {
queue.offer(i); queue.offer(i);
queue.poll(); queue.poll();
console.log("第 " + i + " 轮入队 + 出队后 queue = "); console.log("第 " + i + " 轮入队 + 出队后 queue =", queue.toArray());
console.log(queue.toArray()); console.log(queue.toArray());
} }

View file

@ -7,16 +7,6 @@
import ListNode from './ListNode'; import ListNode from './ListNode';
import { TreeNode } from './TreeNode'; import { TreeNode } from './TreeNode';
class Trunk {
prev: Trunk | null;
str: string;
constructor(prev: Trunk | null, str: string) {
this.prev = prev;
this.str = str;
}
}
/** /**
* Print a linked list * Print a linked list
* @param head * @param head
@ -30,6 +20,16 @@ function printLinkedList(head: ListNode | null): void {
console.log(list.join(' -> ')); console.log(list.join(' -> '));
} }
class Trunk {
prev: Trunk | null;
str: string;
constructor(prev: Trunk | null, str: string) {
this.prev = prev;
this.str = str;
}
}
/** /**
* The interface of the tree printer * The interface of the tree printer
* This tree printer is borrowed from TECHIE DELIGHT * This tree printer is borrowed from TECHIE DELIGHT

View file

@ -12,8 +12,8 @@ pub fn ArrayQueue(comptime T: type) type {
nums: []T = undefined, // nums: []T = undefined, //
cap: usize = 0, // cap: usize = 0, //
front: usize = 0, // front: usize = 0, //
rear: usize = 0, // + 1 queSize: usize = 0, // + 1
mem_arena: ?std.heap.ArenaAllocator = null, mem_arena: ?std.heap.ArenaAllocator = null,
mem_allocator: std.mem.Allocator = undefined, // mem_allocator: std.mem.Allocator = undefined, //
@ -41,13 +41,12 @@ pub fn ArrayQueue(comptime T: type) type {
// //
pub fn size(self: *Self) usize { pub fn size(self: *Self) usize {
// rear < front return self.queSize;
return (self.capacity() + self.rear - self.front) % self.capacity();
} }
// //
pub fn isEmpty(self: *Self) bool { pub fn isEmpty(self: *Self) bool {
return self.rear == self.front; return self.queSize == 0;
} }
// //
@ -56,17 +55,20 @@ pub fn ArrayQueue(comptime T: type) type {
std.debug.print("队列已满\n", .{}); std.debug.print("队列已满\n", .{});
return; return;
} }
// + 1
// rear
var rear = (self.front + self.queSize) % self.capacity();
// num // num
self.nums[self.rear] = num; self.nums[rear] = num;
// self.queSize++;
self.rear = (self.rear + 1) % self.capacity();
} }
// //
pub fn poll(self: *Self) T { pub fn poll(self: *Self) T {
var num = self.peek(); var num = self.peek();
// //
self.front = (self.front + 1) % self.capacity(); self.front = (self.front + 1) % self.capacity();
self.queSize--;
return num; return num;
} }

View file

@ -742,45 +742,52 @@ comments: true
/* 基于环形数组实现的队列 */ /* 基于环形数组实现的队列 */
class ArrayQueue { class ArrayQueue {
private int[] nums; // 用于存储队列元素的数组 private int[] nums; // 用于存储队列元素的数组
private int front = 0; // 头指针,指向队首 private int front; // 队首指针,指向队首元素
private int rear = 0; // 尾指针,指向队尾 + 1 private int queSize; // 队列长度
public ArrayQueue(int capacity) { public ArrayQueue(int capacity) {
// 初始化数组
nums = new int[capacity]; nums = new int[capacity];
front = queSize = 0;
} }
/* 获取队列的容量 */ /* 获取队列的容量 */
public int capacity() { public int capacity() {
return nums.length; return nums.length;
} }
/* 获取队列的长度 */ /* 获取队列的长度 */
public int size() { public int size() {
int capacity = capacity(); return queSize;
// 由于将数组看作为环形,可能 rear < front 因此需要取余数
return (capacity + rear - front) % capacity;
} }
/* 判断队列是否为空 */ /* 判断队列是否为空 */
public boolean isEmpty() { public boolean isEmpty() {
return rear - front == 0; return queSize == 0;
} }
/* 入队 */ /* 入队 */
public void offer(int num) { public void offer(int num) {
if (size() == capacity()) { if (queSize == capacity()) {
System.out.println("队列已满"); System.out.println("队列已满");
return; return;
} }
// 计算尾指针,指向队尾索引 + 1
// 通过取余操作,实现 rear 越过数组尾部后回到头部
int rear = (front + queSize) % capacity();
// 尾结点后添加 num // 尾结点后添加 num
nums[rear] = num; nums[rear] = num;
// 尾指针向后移动一位,越过尾部后返回到数组头部 queSize++;
rear = (rear + 1) % capacity();
} }
/* 出队 */ /* 出队 */
public int poll() { public int poll() {
int num = peek(); int num = peek();
// 队指针向后移动一位,若越过尾部则返回到数组头部 // 队指针向后移动一位,若越过尾部则返回到数组头部
front = (front + 1) % capacity(); front = (front + 1) % capacity();
queSize--;
return num; return num;
} }
/* 访问队首元素 */ /* 访问队首元素 */
public int peek() { public int peek() {
if (isEmpty()) if (isEmpty())
@ -797,49 +804,59 @@ comments: true
class ArrayQueue { class ArrayQueue {
private: private:
int *nums; // 用于存储队列元素的数组 int *nums; // 用于存储队列元素的数组
int cap; // 队列容量 int front; // 队首指针,指向队首元素
int front = 0; // 头指针,指向队首 int queSize; // 队列长度
int rear = 0; // 尾指针,指向队尾 + 1 int queCapacity; // 队列容量
public: public:
ArrayQueue(int capacity) { ArrayQueue(int capacity) {
// 初始化数组 // 初始化数组
cap = capacity;
nums = new int[capacity]; nums = new int[capacity];
queCapacity = capacity;
front = queSize = 0;
} }
~ArrayQueue() { ~ArrayQueue() {
delete[] nums; delete[] nums;
} }
/* 获取队列的容量 */ /* 获取队列的容量 */
int capacity() { int capacity() {
return cap; return queCapacity;
} }
/* 获取队列的长度 */ /* 获取队列的长度 */
int size() { int size() {
// 由于将数组看作为环形,可能 rear < front 因此需要取余数 return queSize;
return (capacity() + rear - front) % capacity();
} }
/* 判断队列是否为空 */ /* 判断队列是否为空 */
bool empty() { bool empty() {
return rear - front == 0; return size() == 0;
} }
/* 入队 */ /* 入队 */
void offer(int num) { void offer(int num) {
if (size() == capacity()) { if (queSize == queCapacity) {
cout << "队列已满" << endl; cout << "队列已满" << endl;
return; return;
} }
// 计算队尾指针,指向队尾索引 + 1
// 通过取余操作,实现 rear 越过数组尾部后回到头部
int rear = (front + queSize) % queCapacity;
// 尾结点后添加 num // 尾结点后添加 num
nums[rear] = num; nums[rear] = num;
// 尾指针向后移动一位,越过尾部后返回到数组头部 queSize++;
rear = (rear + 1) % capacity();
} }
/* 出队 */ /* 出队 */
void poll() { void poll() {
int num = peek(); int num = peek();
// 队头指针向后移动一位,若越过尾部则返回到数组头部 // 队首指针向后移动一位,若越过尾部则返回到数组头部
front = (front + 1) % capacity(); front = (front + 1) % queCapacity;
queSize--;
} }
/* 访问队首元素 */ /* 访问队首元素 */
int peek() { int peek() {
if (empty()) if (empty())
@ -856,8 +873,8 @@ comments: true
class ArrayQueue: class ArrayQueue:
def __init__(self, size): def __init__(self, size):
self.__nums = [0] * size # 用于存储队列元素的数组 self.__nums = [0] * size # 用于存储队列元素的数组
self.__front = 0 # 头指针,指向队首 self.__front = 0 # 队首指针,指向队首元素
self.__rear = 0 # 尾指针,指向队尾 + 1 self.__size = 0 # 队列长度
""" 获取队列的容量 """ """ 获取队列的容量 """
def capacity(self): def capacity(self):
@ -865,45 +882,34 @@ comments: true
""" 获取队列的长度 """ """ 获取队列的长度 """
def size(self): def size(self):
# 由于将数组看作为环形,可能 rear < front 因此需要取余数 return self.__size
return (self.capacity() + self.__rear - self.__front) % self.capacity()
""" 判断队列是否为空 """ """ 判断队列是否为空 """
def is_empty(self): def is_empty(self):
return (self.__rear - self.__front) == 0 return self.__size == 0
""" 入队 """ """ 入队 """
def push(self, val): def push(self, num):
if self.size() == self.capacity(): assert self.__size < self.capacity(), "队列已满"
print("队列已满") # 计算尾指针,指向队尾索引 + 1
return False # 通过取余操作,实现 rear 越过数组尾部后回到头部
rear = (self.__front + self.__size) % self.capacity()
# 尾结点后添加 num # 尾结点后添加 num
self.__nums[self.__rear] = val self.__nums[rear] = num
# 尾指针向后移动一位,越过尾部后返回到数组头部 self.__size += 1
self.__rear = (self.__rear + 1) % self.capacity()
""" 出队 """ """ 出队 """
def poll(self): def poll(self):
num = self.peek() num = self.peek()
# 队指针向后移动一位,若越过尾部则返回到数组头部 # 队指针向后移动一位,若越过尾部则返回到数组头部
self.__front = (self.__front + 1) % self.capacity() self.__front = (self.__front + 1) % self.capacity()
self.__size -= 1
return num return num
""" 访问队首元素 """ """ 访问队首元素 """
def peek(self): def peek(self):
if self.is_empty(): assert not self.is_empty(), "队列为空"
print("队列为空")
return False
return self.__nums[self.__front] return self.__nums[self.__front]
""" 返回列表用于打印 """
def to_list(self):
res = [0] * self.size()
j = self.__front
for i in range(self.size()):
res[i] = self.__nums[(j % self.capacity())]
j += 1
return res
``` ```
=== "Go" === "Go"
@ -911,54 +917,53 @@ comments: true
```go title="array_queue.go" ```go title="array_queue.go"
/* 基于环形数组实现的队列 */ /* 基于环形数组实现的队列 */
type arrayQueue struct { type arrayQueue struct {
data []int // 用于存储队列元素的数组 nums []int // 用于存储队列元素的数组
capacity int // 队列容量(即最多容量的元素个数) front int // 队首指针,指向队首元素
front int // 头指针,指向队首 queSize int // 队列长度
rear int // 尾指针,指向队尾 + 1 queCapacity int // 队列容量(即最大容纳元素数量)
} }
// newArrayQueue 基于环形数组实现的队列 // newArrayQueue 基于环形数组实现的队列
func newArrayQueue(capacity int) *arrayQueue { func newArrayQueue(queCapacity int) *arrayQueue {
return &arrayQueue{ return &arrayQueue{
data: make([]int, capacity), nums: make([]int, queCapacity),
capacity: capacity, queCapacity: queCapacity,
front: 0, front: 0,
rear: 0, queSize: 0,
} }
} }
// size 获取队列的长度 // size 获取队列的长度
func (q *arrayQueue) size() int { func (q *arrayQueue) size() int {
size := (q.capacity + q.rear - q.front) % q.capacity return q.queSize
return size
} }
// isEmpty 判断队列是否为空 // isEmpty 判断队列是否为空
func (q *arrayQueue) isEmpty() bool { func (q *arrayQueue) isEmpty() bool {
return q.rear-q.front == 0 return q.queSize == 0
} }
// offer 入队 // offer 入队
func (q *arrayQueue) offer(v int) { func (q *arrayQueue) offer(num int) {
// 当 rear == capacity 表示队列已满 // 当 rear == queCapacity 表示队列已满
if q.size() == q.capacity { if q.queSize == q.queCapacity {
return return
} }
// 尾结点后添加 // 计算尾指针,指向队尾索引 + 1
q.data[q.rear] = v // 通过取余操作,实现 rear 越过数组尾部后回到头部
// 尾指针向后移动一位,越过尾部后返回到数组头部 rear := (q.front + q.queSize) % q.queCapacity
q.rear = (q.rear + 1) % q.capacity // 尾结点后添加 num
q.nums[rear] = num
q.queSize++
} }
// poll 出队 // poll 出队
func (q *arrayQueue) poll() any { func (q *arrayQueue) poll() any {
if q.isEmpty() { num := q.peek()
return nil // 队首指针向后移动一位,若越过尾部则返回到数组头部
} q.front = (q.front + 1) % q.queCapacity
v := q.data[q.front] q.queSize--
// 队头指针向后移动一位,若越过尾部则返回到数组头部 return num
q.front = (q.front + 1) % q.capacity
return v
} }
// peek 访问队首元素 // peek 访问队首元素
@ -966,8 +971,17 @@ comments: true
if q.isEmpty() { if q.isEmpty() {
return nil return nil
} }
v := q.data[q.front] return q.nums[q.front]
return v }
// 获取 Slice 用于打印
func (q *arrayQueue) toSlice() []int {
rear := (q.front + q.queSize)
if rear >= q.queCapacity {
rear %= q.queCapacity
return append(q.nums[q.front:], q.nums[:rear]...)
}
return q.nums[q.front:rear]
} }
``` ```
@ -976,46 +990,55 @@ comments: true
```js title="array_queue.js" ```js title="array_queue.js"
/* 基于环形数组实现的队列 */ /* 基于环形数组实现的队列 */
class ArrayQueue { class ArrayQueue {
#queue; // 用于存储队列元素的数组 #nums; // 用于存储队列元素的数组
#front = 0; // 头指针,指向队首 #front = 0; // 队首指针,指向队首元素
#rear = 0; // 尾指针,指向队尾 + 1 #queSize = 0; // 队列长度
constructor(capacity) { constructor(capacity) {
this.#queue = new Array(capacity); this.#nums = new Array(capacity);
} }
/* 获取队列的容量 */ /* 获取队列的容量 */
get capacity() { get capacity() {
return this.#queue.length; return this.#nums.length;
} }
/* 获取队列的长度 */ /* 获取队列的长度 */
get size() { get size() {
// 由于将数组看作为环形,可能 rear < front 因此需要取余数 return this.#queSize;
return (this.capacity + this.#rear - this.#front) % this.capacity;
} }
/* 判断队列是否为空 */ /* 判断队列是否为空 */
empty() { empty() {
return this.#rear - this.#front == 0; return this.#queSize == 0;
} }
/* 入队 */ /* 入队 */
offer(num) { offer(num) {
if (this.size == this.capacity) if (this.size == this.capacity)
throw new Error("队列已满"); throw new Error("队列已满");
// 计算尾指针,指向队尾索引 + 1
// 通过取余操作,实现 rear 越过数组尾部后回到头部
const rear = (this.#front + this.size) % this.capacity;
// 尾结点后添加 num // 尾结点后添加 num
this.#queue[this.#rear] = num; this.#nums[rear] = num;
// 尾指针向后移动一位,越过尾部后返回到数组头部 this.#queSize++;
this.#rear = (this.#rear + 1) % this.capacity;
} }
/* 出队 */ /* 出队 */
poll() { poll() {
const num = this.peek(); const num = this.peek();
// 队指针向后移动一位,若越过尾部则返回到数组头部 // 队指针向后移动一位,若越过尾部则返回到数组头部
this.#front = (this.#front + 1) % this.capacity; this.#front = (this.#front + 1) % this.capacity;
this.#queSize--;
return num; return num;
} }
/* 访问队首元素 */ /* 访问队首元素 */
peek() { peek() {
if (this.empty()) if (this.empty())
throw new Error("队列为空"); throw new Error("队列为空");
return this.#queue[this.#front]; return this.#nums[this.#front];
} }
} }
``` ```
@ -1025,47 +1048,56 @@ comments: true
```typescript title="array_queue.ts" ```typescript title="array_queue.ts"
/* 基于环形数组实现的队列 */ /* 基于环形数组实现的队列 */
class ArrayQueue { class ArrayQueue {
private queue: number[]; // 用于存储队列元素的数组 private nums: number[]; // 用于存储队列元素的数组
private front: number = 0; // 头指针,指向队首 private front: number; // 队首指针,指向队首元素
private rear: number = 0; // 尾指针,指向队尾 + 1 private queSize: number; // 队列长度
private CAPACITY: number = 1e5;
constructor(capacity?: number) { constructor(capacity: number) {
this.queue = new Array<number>(capacity ?? this.CAPACITY); this.nums = new Array<number>(capacity);
this.front = this.queSize = 0;
} }
/* 获取队列的容量 */ /* 获取队列的容量 */
get capacity(): number { get capacity(): number {
return this.queue.length; return this.nums.length;
} }
/* 获取队列的长度 */ /* 获取队列的长度 */
get size(): number { get size(): number {
// 由于将数组看作为环形,可能 rear < front 因此需要取余数 return this.queSize;
return (this.capacity + this.rear - this.front) % this.capacity;
} }
/* 判断队列是否为空 */ /* 判断队列是否为空 */
empty(): boolean { empty(): boolean {
return this.rear - this.front == 0; return this.queSize == 0;
} }
/* 入队 */ /* 入队 */
offer(num: number): void { offer(num: number): void {
if (this.size == this.capacity) if (this.size == this.capacity)
throw new Error("队列已满"); throw new Error("队列已满");
// 计算尾指针,指向队尾索引 + 1
// 通过取余操作,实现 rear 越过数组尾部后回到头部
const rear = (this.front + this.queSize) % this.capacity;
// 尾结点后添加 num // 尾结点后添加 num
this.queue[this.rear] = num; this.nums[rear] = num;
// 尾指针向后移动一位,越过尾部后返回到数组头部 this.queSize++;
this.rear = (this.rear + 1) % this.capacity;
} }
/* 出队 */ /* 出队 */
poll(): number { poll(): number {
const num = this.peek(); const num = this.peek();
// 队指针向后移动一位,若越过尾部则返回到数组头部 // 队指针向后移动一位,若越过尾部则返回到数组头部
this.front = (this.front + 1) % this.capacity; this.front = (this.front + 1) % this.capacity;
this.queSize--;
return num; return num;
} }
/* 访问队首元素 */ /* 访问队首元素 */
peek(): number { peek(): number {
if (this.empty()) if (this.empty())
throw new Error("队列为空"); throw new Error("队列为空");
return this.queue[this.front]; return this.nums[this.front];
} }
} }
``` ```
@ -1083,51 +1115,59 @@ comments: true
class ArrayQueue class ArrayQueue
{ {
private int[] nums; // 用于存储队列元素的数组 private int[] nums; // 用于存储队列元素的数组
private int front = 0; // 头指针,指向队首 private int front; // 队首指针,指向队首元素
private int rear = 0; // 尾指针,指向队尾 + 1 private int queSize; // 队列长度
public ArrayQueue(int capacity) public ArrayQueue(int capacity)
{ {
// 初始化数组
nums = new int[capacity]; nums = new int[capacity];
front = queSize = 0;
} }
/* 获取队列的容量 */ /* 获取队列的容量 */
public int capacity() public int capacity()
{ {
return nums.Length; return nums.Length;
} }
/* 获取队列的长度 */ /* 获取队列的长度 */
public int size() public int size()
{ {
int capacity = this.capacity(); return queSize;
// 由于将数组看作为环形,可能 rear < front 因此需要取余数
return (capacity + rear - front) % capacity;
} }
/* 判断队列是否为空 */ /* 判断队列是否为空 */
public bool isEmpty() public bool isEmpty()
{ {
return rear - front == 0; return queSize == 0;
} }
/* 入队 */ /* 入队 */
public void offer(int num) public void offer(int num)
{ {
if (size() == capacity()) if (queSize == capacity())
{ {
Console.WriteLine("队列已满"); Console.WriteLine("队列已满");
return; return;
} }
// 计算尾指针,指向队尾索引 + 1
// 通过取余操作,实现 rear 越过数组尾部后回到头部
int rear = (front + queSize) % capacity();
// 尾结点后添加 num // 尾结点后添加 num
nums[rear] = num; nums[rear] = num;
// 尾指针向后移动一位,越过尾部后返回到数组头部 queSize++;
rear = (rear + 1) % capacity();
} }
/* 出队 */ /* 出队 */
public int poll() public int poll()
{ {
int num = peek(); int num = peek();
// 队指针向后移动一位,若越过尾部则返回到数组头部 // 队指针向后移动一位,若越过尾部则返回到数组头部
front = (front + 1) % capacity(); front = (front + 1) % capacity();
queSize--;
return num; return num;
} }
/* 访问队首元素 */ /* 访问队首元素 */
public int peek() public int peek()
{ {
@ -1144,8 +1184,8 @@ comments: true
/* 基于环形数组实现的队列 */ /* 基于环形数组实现的队列 */
class ArrayQueue { class ArrayQueue {
private var nums: [Int] // 用于存储队列元素的数组 private var nums: [Int] // 用于存储队列元素的数组
private var front = 0 // 头指针,指向队首 private var front = 0 // 队首指针,指向队首元素
private var rear = 0 // 尾指针,指向队尾 + 1 private var queSize = 0 // 队列长度
init(capacity: Int) { init(capacity: Int) {
// 初始化数组 // 初始化数组
@ -1159,14 +1199,12 @@ comments: true
/* 获取队列的长度 */ /* 获取队列的长度 */
func size() -> Int { func size() -> Int {
let capacity = capacity() queSize
// 由于将数组看作为环形,可能 rear < front 因此需要取余数
return (capacity + rear - front) % capacity
} }
/* 判断队列是否为空 */ /* 判断队列是否为空 */
func isEmpty() -> Bool { func isEmpty() -> Bool {
rear - front == 0 queSize == 0
} }
/* 入队 */ /* 入队 */
@ -1175,19 +1213,22 @@ comments: true
print("队列已满") print("队列已满")
return return
} }
// 计算尾指针,指向队尾索引 + 1
// 通过取余操作,实现 rear 越过数组尾部后回到头部
int rear = (front + queSize) % capacity();
// 尾结点后添加 num // 尾结点后添加 num
nums[rear] = num nums[rear] = num;
// 尾指针向后移动一位,越过尾部后返回到数组头部 queSize++;
rear = (rear + 1) % capacity()
} }
/* 出队 */ /* 出队 */
@discardableResult @discardableResult
func poll() -> Int { func poll() -> Int {
let num = peek() let num = peek()
// 队头指针向后移动一位,若越过尾部则返回到数组头部 // 队首指针向后移动一位,若越过尾部则返回到数组头部
front = (front + 1) % capacity() front = (front + 1) % capacity();
return num queSize--;
return num;
} }
/* 访问队首元素 */ /* 访问队首元素 */