队列 -- 链表 -- C语言

队列有一些特殊的队列:循环队列、阻塞队列、并发队列,基本都用数组实现....这篇是链表


队列用于什么地方呢?

大家都知道,CPU 资源是有限的,过多的线程反而会导致 CPU 频繁切换,处理性能下降。所以,线程池的大小一般都是综合考虑要处理任务的特点和硬件环境,来事先设置的。

当我们向固定大小的线程池中请求一个线程时,如果线程池中没有空闲资源了,这个时候线程池是拒绝请求还是排队请求?各种处理策略又是怎么实现的呢?都会用到队列


个人理解的线程,就是你的要求,你打开QQ,微信,浏览器等等这些相当于给CPU任务,CPU会给你执行,但是一下子打开太多,没有多余空间了,这个时候是拒绝呢,还是排队,有空了给你执行?


目录

1. 头文件

2. 结构体

3. 创建空队列

4. 摧毁队列链表

5. 插入队列元素

6. 删除队列元素

7. 输出队列元素

8. 主函数


1. 头文件

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

2. 结构体

/*结点*/
typedef struct ListQueueNode {
	int data;
	struct ListQueueNode* next;
}stListQueueNode;
/*列表*/
typedef struct ListQueue {
	int num;
	stListQueueNode* head;
	stListQueueNode* tail;
}stListQueue;

3. 创建空队列

stListQueue* listQueue_create() {
	stListQueue* queue = NULL;
	queue = (stListQueue*)malloc(sizeof(stListQueue));
	if (queue == NULL) {
		return NULL;
	}
	queue->num = 0;
	queue->head = NULL;
	queue->tail = NULL;
	return queue;
}

4. 摧毁队列链表

void listQueue_destory(stListQueue* queue){
	int data = 0;
	if (queue == NULL || queue->num == 0) {
		return;
	}
	while (queue->num != 0) {
		listQueue_dequeue(queue, &data);
		queue->num--;
	}
	free(queue);
	return;
}

5. 插入队列元素

int listQueue_enqueue(stListQueue* queue, int data) {
	stListQueueNode* ptmp = NULL;
	if (queue == NULL) {
		return -1;
	}
	ptmp = (stListQueueNode*)malloc(sizeof(stListQueueNode));
	if (ptmp == NULL) {
		return -1;
	}                                         //以上创建空链表

	ptmp->data = data;
	ptmp->next = NULL;                        //赋值

	/*注意,空队列情况!!*/
	if(queue->head == NULL){
		queue->head = ptmp;
	}
	else {
		queue->tail->next = ptmp;
	}
	queue->tail = ptmp;
	queue->num++;                             //将队列数加一
	return 0;
}

6. 删除队列元素

int listQueue_dequeue(stListQueue* queue, int* data) {
	stListQueueNode* ptmp = NULL;
	if (queue == NULL || queue->num == NULL || data == NULL) {
		return -1;
	}

	/*返回删除值*/
	*data = queue->head->data;

	ptmp = queue->head;
	queue->head = ptmp->next;
	queue->num--;

	/*队列是否为空*/
	if (queue->head == NULL) {
		queue->tail = NULL;
	}
	/*不要忘记释放空间*/
	free(ptmp);
	return 0;
}

7. 输出队列元素

void listQueue_dump(stListQueue* queue) {
	stListQueueNode* ptmp = NULL;
	if (queue == NULL || queue->num == 0) {
		return;
	}

	ptmp = queue->head;
	while (ptmp != NULL) {
		printf("%d ", ptmp->data);
		ptmp = ptmp->next;
	}
    printf("\n");
	return;
}

8. 主函数

int main() {
	int data = 0;
	int ret = 0;
 
	stListQueue* queue = NULL;                         //创建空队列
	queue = listQueue_create();
	if (queue == NULL) {
		printf("queue create falied.\n");
		return 0;
	}

	int q = 0;                                          //从键盘读入数据
	printf("请输入插入队列的值(输入100结束插入):\n");
	while (q != 100) {
		scanf_s("%d", &q);
		listQueue_enqueue(queue, q);
	}
	listQueue_dump(queue);

	ret = listQueue_dequeue(queue, &data);              //删除队列元素(先入先出)
	if (ret != 0) {
		printf("queue %d falied\n", data);
	}
	printf("queue dequeue %d\n", data);
	listQueue_dump(queue);

	listQueue_destory(queue);                           //销毁队列
	return 0;
}

循环队列 和 普通数组队列的【差别】在于:

结束条件 : head == tail     ==== 》    (tail+1)%n=head    

假设数组大小为n == 10 ,当 tail == 5 时 ,(5+1)%10 = 6 ,但当 tail == 9 时,(9+1)% 10= 0 ,队列的第一个元素 ,开始循环了

开始条件 head = 0, tail = 0, 加元素 tail 向后移,去元素 head 向后移

结束条件 head = 6 , tail = 5 , 再加一个元素 (5+1)% 10 == 6 , 队满 , (tail+1)%n=head 。  

 

 

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值