用數組實現的隊列,也叫循環隊列。就是定義一個數組,用兩個下標front,rear表示隊頭和隊尾。當隊頭和隊尾相等時,隊列為空。當隊尾+1等於隊頭時,隊列為滿。這樣會浪費一個內存空間。還可以定義一個變量,表示隊列空滿。
我們下面介紹的是第一種方法。
我們可以把數組想象成一個圓形,數組當然不會是圓形,我們可以根據取余來判斷數組的下標是否還在數組范圍內。
我們在定義數組時會給定一個數組的大小,也就是MAXSIZE,大家會在很多函數中看到對MAXSIZE取余,這是為了保證數組的下標在有效的范圍內。
當front和rear在同一個位置時,隊列為空。
當front == rear + 1時,為滿,也就是rear在front后面。(front == (rear+1)%MAXSIZE;)//判斷條件。大家可以用實際的數字試一下。
aqueue.h
#ifndef _QUEUE_H
#define _QUEUE_H
#define MAXSIZE 10
typedef struct queue
{
int * arr;
int front;
int rear;
} Queue;
void q_init(Queue * queue);//初始化
void q_push(Queue * queue, const int data);//入隊
void q_pop(Queue * queue);//出隊
bool q_empty(Queue * queue);//為空
bool q_full(Queue * queue);//為滿
int q_size(Queue * queue);//隊大小
int q_front(Queue * queue);//隊頭元素
int q_back(Queue * queue);//隊尾元素
void q_destroy(Queue * queue);//銷毀
#endif //_QUEUE_h
aqueue.c
#include <stdio.h> #include <stdlib.h> #include <assert.h> #include <stdbool.h> #include "aqueue.h" void q_init(Queue * queue) { queue->arr = (int *)malloc( sizeof(int) * MAXSIZE );//初始化數組 assert(queue->arr != NULL); queue->front = 0; queue->rear = 0; } void q_push(Queue * queue, const int data) { if ( q_full(queue) ) return; queue->arr[queue->rear++] = data;//入隊,隊尾+1 queue->rear = queue->rear % MAXSIZE;//如果隊尾 } void q_pop(Queue * queue) { if ( q_empty(queue) ) return; queue->front = ++queue->front % MAXSIZE;//front+1,對MAXSIZE取余 } bool q_empty(Queue * queue) { return queue->front == queue->rear; } bool q_full(Queue * queue) { return queue->front == (queue->rear + 1) % MAXSIZE; int q_size(Queue * queue) { return (queue->rear - queue->front) % MAXSIZE; } int q_front(Queue * queue) { assert( !q_empty(queue) ); return queue->arr[queue->front]; } int q_back(Queue * queue) { assert( !q_empty(queue) ); return queue->arr[queue->rear - 1]; } void q_destroy(Queue * queue) { free(queue->arr); }
循環隊列最好多入隊出隊的測試幾次。因為可能下標沒有轉圈時是好使,轉圈之后就不好使了。
還需要把數算明白。