【数据结构】-队列概述和操作

一、队列概述

        队列是一个特殊的线性表,不能在线性表的中间位置进行操作,只能在线性表的两端进行操作

        1.队头(front):线性表的表头,数据的删除端实现数据的删除操作,称数据元素的出队。

        2.队尾(rear):线性表的表尾,数据的插入端实现数据的插入操作,称数据元素的入队。

        队列的特性:先进先出

二、队列的顺序存储

        顺序队列的存储空间:

        1.顺序队列元素在操作之前,需要实现空间的开辟,开辟的空间大小固定;

        2.在操作过程中,由于入队和出队都会是元素存储位置序号的递增,序号递增到空间最大序号值,最终可存储数据的个数有限;

        3.每一个存储位置只能实现一个数据元素的入队和出队操作,空间只会使用一次,不会再次使用,会导致空间利用率较低。

        顺序队列定义

typedef int data_t; //队列中数据元素的类型

struct sqqueue{
    data_t *data; //动态开辟的首元素地址
    int nmenmb; //空间中可存储元素的个数
    int front;// 队头元素存储序号标签
    int rear; //队尾元素存储序号标签
}sqqueue_t;

三、顺序循环队列

        顺序循环队列实质是对顺序队列的优化,在遍历到空间最大的序号时,序号回到0开始继续向后办理。

        循序队列的构建:

                实质是创建连续的顺序存储空间,在访问时构建循环访问;

                入队访问:队尾元素rear序号操作,rear = (rear+1)% nmemb;

                出队访问:队头元素front序号操作,front = (front+1)% nmemb;

        队尾rear和队头front初始值规定:

                ①front指向队头元素的前一个位置,rear指向队尾元素所在位置;

                ②front指向队头元素所在位置,rear指向队尾的下一个位置。

        队为空的条件:

                rear == front

        队为满的条件:

                按规定也为rear == front ,为了区分,队为满的元素个数=nmemb-1;

        若采用②规定:

                front和rear的默认初始值设为:front = 0;rear = 0;

              队为空的条件还是:rear == front;

                队为满的条件,需要牺牲一个空间来区别队列为空还是满:

                        1)rear > front  ==>front == (rear+1)%nmemb;

                        2) rear < front ==>front ==raer + 1 <=> front == (rear+1)%nmemb;

              综上:队满条件: front == (rear+1)%nmemb

四、相关操作

头文件:common.h

#ifndef _COMMON_H_
#define _COMMON_H_
typedef int data_t;

typedef struct queue{
        data_t *data;
        int nmemb;
        int front;
        int rear;
} sqqueue_t;

sqqueue_t *CreateSqQueue(int mynmemb);//初始化
int EnSqQueue(sqqueue_t *queue,data_t mydata);//入队
int GetSqQueue(sqqueue_t *queue,data_t *mydata);//查看对头元素
int DeSqQueue(sqqueue_t *queue);//出队



#endif

函数实现: sqqueue.c

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

#include "common.h"

sqqueue_t *CreateSqQueue(int mynmemb)//初始化
{
	sqqueue_t *queue = malloc(sizeof(sqqueue_t));
	if(queue == NULL)
		return NULL;
	queue->data = calloc(mynmemb,sizeof(data_t));
	if(queue->data == NULL){
		free(queue);
		return NULL;
	}
	queue->nmemb = mynmemb;
	queue->front = 0;
	queue->rear = 0;

	return queue;
}
int EnSqQueue(sqqueue_t *queue,data_t mydata)//入队
{
	//判断队满
	if(queue->front == (queue->rear+1)%queue->nmemb)
		return -1;
	//放数据
	queue->data[queue->rear] = mydata;
	queue->rear = (queue->rear+1)%queue->nmemb;

	return 0;
}
int GetSqQueue(sqqueue_t *queue,data_t *mydata)//查看对头元素
{
	//判断是否为空
	if(queue->front == queue->rear)
		return-1;
	*mydata = queue->data[queue->front];
	return 0;
}
int DeSqQueue(sqqueue_t *queue)//出队
{
	//判断是否为空
	if(queue->front == queue->rear)
		return -1;
	queue->front = (queue->front+1)%queue->nmemb;

	return 0;
}

主函数调用:app.c

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

#include "common.h"

int main()
{
	int i;
	sqqueue_t *queue;
	data_t mydata;
	
	queue = CreateSqQueue(10);
	if (queue == NULL)
		return -1;
	i = 20;
	while(i) {
		if (EnSqQueue(queue, i--) == -1) {
			printf("%d En Fail\n", i);
		}
	}
	
	while(GetSqQueue(queue, &mydata) == 0) {
		printf("De : %d\n", mydata);
		DeSqQueue(queue);
	}

}

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值