鱼C论坛

 找回密码
 立即注册
查看: 1959|回复: 0

[学习笔记] 007-队列

[复制链接]
发表于 2018-9-26 23:02:34 | 显示全部楼层 |阅读模式

马上注册,结交更多好友,享用更多功能^_^

您需要 登录 才可以下载或查看,没有账号?立即注册

x
1、基本概念
队列(queue)是一种 特殊的线性表
队列仅在线性表的两端进行操作;
队头(Front):取出数据元素的一端;
队尾(Rear):   插入数据元素的一端。
队列不允许在中间位置插入元素或其他操作。
        队列是只允许在一端进行插入操作,在另一端进行删除操作的线性表。是一种先进先出的线性表(FIFO).
112.jpg

常用操作:
        创建队列;
        销毁队列;
        清空队列;
        进队列;
        出队列;
        获取队头元素;
        获取队列的长度。
2、队列的线性存储
      同样由于队列是一种特殊的线性表,其实现也是可以通过线性表来完成的。
通过线性表的顺序存储来实现队列的顺序 存储。
  1. // 创建一个队列  相当于 创建一个线性表
  2. SeqQueue* SeqQueue_Create(int capacity)
  3. {
  4.         return SeqList_Create(capacity);
  5. }

  6. // 销毁一个队列  相当于 销毁一个线性表
  7. void SeqQueue_Destroy(SeqQueue* queue)
  8. {
  9.         SeqList_Destroy(queue);
  10. }

  11. // 清空一个队列  相当于 清空一个线性表
  12. void SeqQueue_Clear(SeqQueue* queue)
  13. {
  14.         SeqList_Clear(queue);
  15. }

  16. // 入队  相当于 向线性表添加一个元素
  17. // 头插、尾插都可以,这里选择尾插法
  18. int SeqQueue_Append(SeqQueue* queue, void* item)
  19. {
  20.         return SeqList_Insert(queue, item, SeqQueue_Length(queue));
  21. }

  22. // 出队 相当于 删除链表头部元素
  23. void* SeqQueue_Retrieve(SeqQueue* queue)
  24. {
  25.         return SeqList_Delete(queue, 0);
  26. }

  27. // 获取队列头部元素 相当于 获取线性表头部元素
  28. void* SeqQueue_Header(SeqQueue* queue)
  29. {
  30.         return SeqList_Get(queue, 0);
  31. }

  32. // 获取队列长度  相当于 获取线性表长度
  33. int SeqQueue_Length(SeqQueue* queue)
  34. {
  35.         return SeqList_Length(queue);
  36. }

  37. // 获取队列容量  相当于 获取线性表容量
  38. int SeqQueue_Capacity(SeqQueue* queue)
  39. {
  40.         return SeqList_Capacity(queue);
  41. }
复制代码

3、队列的链式存储
和栈类似,队列的链式存储同样涉及到  ① 队列的业务结点向线性表业务结点的转换    ② 结点的生命周期的管理。
  1. // 队列也是一种特殊的线性表
  2. // 队列的业务结点的数据结构
  3. typedef struct _tag_LinkQueueNode
  4. {
  5.         LinkListNode node;
  6.         void* item;
  7. }TLinkQueueNode;



  8. // 创建一个队列  相当于 创建一个线性表
  9. LinkQueue* LinkQueue_Create()
  10. {
  11.         return LinkList_Create();
  12. }

  13. // 销毁一个队列  相当于 销毁一个线性表
  14. // 结点的内存管理
  15. void LinkQueue_Destroy(LinkQueue* queue)
  16. {
  17.         LinkQueue_Clear(queue);
  18.         LinkList_Destroy(queue);
  19. }


  20. // 清空一个队列  需要把队列里的每个元素取出来  释放掉
  21. void LinkQueue_Clear(LinkQueue* queue)
  22. {
  23.         while (LinkQueue_Length(queue) > 0)
  24.         {
  25.                 LinkQueue_Retrieve(queue);
  26.         }
  27.         LinkList_Clear(queue);
  28. }


  29. // 入队  相当于 向线性表添加一个元素
  30. // 头插、尾插都可以,这里选择尾插法
  31. int LinkQueue_Append(LinkQueue* queue, void* item)
  32. {
  33.         int ret = 0;
  34.         TLinkQueueNode *tmp = NULL;
  35.         tmp = (TLinkQueueNode*)malloc(sizeof(TLinkQueueNode));
  36.         if (tmp == NULL)
  37.         {
  38.                 ret = -1;
  39.                 printf("Fun LinkQueue_Append() malloc error:%d", ret);
  40.                 return ret;
  41.         }
  42.         memset(tmp, 0, sizeof(TLinkQueueNode));
  43.         tmp->item = item;
  44.         // 需要把队列的业务结点 转换为 线性表的业务结点
  45.         ret = LinkList_Insert(queue, (LinkListNode*)tmp, LinkList_Length(queue));
  46.         if (ret != 0)
  47.         {
  48.                 printf("Fun LinkList_Insert() error: %d\n", ret);
  49.                 if (tmp != NULL)
  50.                 {
  51.                         free(tmp);
  52.                         tmp = NULL;
  53.                 }
  54.         }
  55.         return ret;
  56. }

  57. // 从队列中删除一个元素 相当于  从线性表中删除一个元素
  58. void* LinkQueue_Retrieve(LinkQueue* queue)
  59. {
  60.         TLinkQueueNode *tmp = NULL;
  61.         void                   *ret = NULL;
  62.         tmp = (TLinkQueueNode*)LinkList_Delete(queue, 0);
  63.         if (tmp == NULL)
  64.         {
  65.                 printf("Fun LinkList_Delete error\n");
  66.                 return NULL;
  67.         }
  68.         ret = tmp->item;
  69.         if (tmp != NULL)
  70.         {
  71.                 free(tmp);
  72.         }
  73.         return ret;
  74. }

  75. // 获取队列中头部元素 相当于  获取线性表的头部元素
  76. void* LinkQueue_Header(LinkQueue* queue)
  77. {
  78.         TLinkQueueNode *tmp = NULL;
  79.         void                   *ret = NULL;
  80.         tmp = LinkList_Get(queue, 0);
  81.         if (tmp == NULL)
  82.         {
  83.                 printf("func LinkList_Get() reeor\n");
  84.                 return NULL;
  85.         }
  86.         return tmp->item;
  87. }

  88. // 求队列的长度 相当于 求线性表的长度
  89. int LinkQueue_Length(LinkQueue* queue)
  90. {
  91.         return LinkList_Length(queue);
  92. }
复制代码

完整代码: 队列的顺序存储.zip (2.72 KB, 下载次数: 5)
                 队列的链式存储.zip (2.98 KB, 下载次数: 6)

本帖被以下淘专辑推荐:

小甲鱼最新课程 -> https://ilovefishc.com
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

小黑屋|手机版|Archiver|鱼C工作室 ( 粤ICP备18085999号-1 | 粤公网安备 44051102000585号)

GMT+8, 2025-6-8 21:58

Powered by Discuz! X3.4

© 2001-2023 Discuz! Team.

快速回复 返回顶部 返回列表