队列

为了操作上的方便,我们将队头指针指向链队列的头结点,而队尾指针指向终端结点。一个普通的链队列大概是下面这个样子:

当队列为空时,front和rear都指向头结点。

链队列的结构体定义

  • 与链栈一样,我们分两步定义链队列的结构体,首先是按链表来定义链队列的结点。
/* QElemType类型根据实际情况而定,这里假设为int */
typedef int QElemType;

typedef struct QNode	/* 结点结构 */
{
    QElemType data;
    struct QNode *next;
} QNode,*QueuePtr;


  • 然后再定义 LinkQueue 的结构体。实际上只要定义队头和队尾指针就可以了。
typedef struct			/* 队列的链表结构 */
{
    QueuePtr front,rear; /* 队头、队尾指针 */
} LinkQueue;


合起来,链队列的结构体定义为:

view source
print ?
#include "stdio.h"

/* QElemType类型根据实际情况而定,这里假设为int */
typedef int QElemType;

typedef struct QNode	/* 结点结构 */
{
    QElemType data;
    struct QNode *next;
} QNode,*QueuePtr;

typedef struct			/* 队列的链表结构 */
{
    QueuePtr front,rear; /* 队头、队尾指针 */
} LinkQueue;

int main()
{
    return 0;
}

#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#include <malloc.h>
#include<assert.h>

//队列有像个主要元素,第一个是队首,另一个是队尾,,,,,而队首和队尾都是一个对象,该对象包含一个数值和指向下一个对象的指针

//对象的定义,,简单的一般用结构进行定义
typedef struct QNode
{
    int nValue;
    struct QNode *pNext;
    
}QNode, *PQNode;
//队列结构里,包含两个数据成员,是队首和队尾,,,,,对象就像普通的int  double之类的数据类型,,只不过数据类型是PQNode
typedef struct 
{
    PQNode pHead;
    PQNode pTail;
}LinkQueue;

void Create(LinkQueue *pLink)              //创建队列,,,初始化两个数据成员,队首队尾,初始化时队首和队尾两者相同,指向同一个内存空间,
{
    PQNode pTmp = (PQNode)malloc(sizeof(QNode));      //开辟一个内存空间    
    pLink->pHead = pLink->pTail = pTmp;              //队首和队尾都指向这一地址
    if (pLink == NULL)
    {
        exit(0);
    }
    pLink->pHead->pNext = NULL;                      //对象的指针指向空地址
    pLink->pHead->nValue = 0;
}

void EnQueue(LinkQueue *pLink, int nValue)                     //进队列操作
{
    PQNode pTmp = (PQNode)malloc(sizeof(QNode));               //首先开辟一个内存存储数据和指向下一个对象的指针
    pTmp->nValue = nValue;
    pTmp->pNext = NULL;

    pLink->pTail->pNext = pTmp;                               //表示在初始队尾指向的下一个指针指向插入的对象,相当于队首指向插入的对象,这样吧插入的对象地址嵌套连接起来了
	                                                         //表示地址的连接性,
    pLink->pTail = pTmp;                           //队尾移位到插入的地址,层级结构,一级一级的指向
}

int DeQueue(LinkQueue *pLink)                         //队列的出输出操作,是先进先出,,从队首开始
{
    if (pLink->pHead == pLink->pTail)                         //首先判断队列是不是空的,空的条件是队首和队尾指向同一个地址
    {//队列为空
        printf("队列为空,无法出队!\n");
    }
    PQNode pTmp = pLink->pHead->pNext;             //输出从队首开始的,取出队首指向的对象,
    pLink->pHead->pNext = pTmp->pNext;              //让队首指向取出对象的下一个对象,则表示对象被取出
    
    if (pLink->pTail == pTmp)                      
    {//若队列中只有一个元素,则出队后要修改队尾指针
        pLink->pTail = pLink->pHead;
    }
    int nValue = pTmp->nValue;
    free(pTmp);                              //释放内存空间
    pTmp = NULL;                            //将该定义清空

    return nValue;
}

bool IsEmpty(LinkQueue *pLink)
{
    return pLink->pHead == pLink->pTail;
}                                                    //判断队列是不空的,条件是队首和队尾指向同一个地址

void DestroyQueue(LinkQueue *pLink)                   //销毁队列,就是把队列中的对象中的内存释放
{
    while (pLink->pHead != NULL)                    
    {
        pLink->pTail = pLink->pHead->pNext;
        free(pLink->pHead);
        pLink->pHead = pLink->pTail;
    }                                       
}                                    
int main()
{
    LinkQueue *pLink = (LinkQueue *)malloc(sizeof(LinkQueue));
    Create(pLink);
	int i;
    for (i = 0; i < 10; i++)
    {
        EnQueue(pLink, i);
    }
    
    for (i = 0; i < 10; i++)
    {
        printf("%d ", DeQueue(pLink));
    }

    DestroyQueue(pLink);
	system("pause");
    return 0;
}


你可能感兴趣的:(队列)