队列(Queue)
一般的顺序队列:
由于这种结构会有假溢出的情况,所以一般不选择这种队列,而更多的使用循环队列。
循环队列:
判断队列满的情况:
1、count来计数;通常使用count
Count等于队列的MAXSIZE
2、Flag标志 int
入队列 flag=1 出队列flag=0
Front=rear&&flag==0
3、把一个存储单元空出来,不存放数据
Rear+1==front
注意事项:(不要) 顺序结构,SeqQueue myQueue;
链式:malloc
初始化:
1 //(1)初始化 2 void SeqQueueInit(SeqQueue *Q) 3 { 4 Q->front = 0; 5 Q->rear = 0; 6 Q->count = 0; 7 } 8 9 10 //(2)入队 11 int SeqQueueIn(SeqQueue *Q, int data) 12 { 13 if (Q->count > 0 && Q->rear == Q->front) 14 { 15 printf("队列满!\n"); 16 return 0; 17 } 18 else 19 { 20 Q->data[Q->rear] = data; //把数据赋给队尾元素 21 Q->rear = (Q->rear + 1) % MAXSIZE; //让对位移动一个位置+1 22 Q->count++; //计数器+1 23 return 1; 24 } 25 } 26 27 28 //(3)出队列 29 int SeqQueueOut(SeqQueue *Q,int *data) 30 { 31 if (Q->count == 0) 32 { 33 printf("队列空\n"); 34 return 0; 35 } 36 else 37 { 38 *data = Q->data[Q->front]; 39 Q->front = (Q->front + 1) % MAXSIZE; 40 Q->count--; 41 } 42 }
//释放:
不要,数组是连续的存储空间,队列的大小10,队列里面有没有内容,都是10个大小。
链式,链表的时候,想要一块内存,开一块,删除之后。
//count是计数 记什么数?队列里面当前的数据的个数。队列的大小是10,存放了3个数据 count=3.
//为什么要取余数
假设:MAXSIZE 10
Rear 0 入队的时候 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 就不属于循环
(Rear+1)% 10 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2345678901234567890123456789
计算机或者手机:硬件的配置已经非常高。
计算机:最大的瓶颈是什么? 机械硬盘 5400 7200读写的速度严重限制计算机的功能,固态硬盘,芯片,120G 好几百 256G IT 500G 60G 32G
//链式的 要不要循环?
1 #include2 #include 3 4 typedef struct node //一个节点的信息 5 { 6 int data; 7 struct node *pnext; 8 }Qnode; 9 10 typedef struct //队列 队头 对位 11 { 12 Qnode *front; //队头的节点 13 Qnode *rear; //队尾节点 14 }Queue; 15 16 17 //初始化 18 void LQueueInit(Queue*); 19 //入队 20 void LQueueIn(Queue*, int); 21 //出队列 22 int LQueueOut(Queue*, int*); 23 24 25 int main() //计算机有时候有些事情先做 26 { 27 int data; 28 Queue myQueue; 29 LQueueInit(&myQueue); 30 31 for (int i = 0; i < 10; i++) 32 { 33 LQueueIn(&myQueue, i + 1); //1 2 3 4 5 6 7 8 9 10 34 } 35 36 for (int i = 0; i < 10; i++) 37 { 38 LQueueOut(&myQueue, &data); 39 printf("%d\t", data); 40 } 41 42 43 printf("front=%d\nrear=%d\n", myQueue.front, myQueue.rear); 44 45 LQueueIn(&myQueue, 11); //11 46 printf("front=%d\nrear=%d\n", myQueue.front, myQueue.rear); //一个节点 指向同一个位置 47 48 LQueueIn(&myQueue, 12); 49 printf("front=%d\nrear=%d\n", myQueue.front, myQueue.rear); 50 51 return 0; 52 } 53 54 55 //初始化 56 void LQueueInit(Queue *Q) //带空头节点的栈 57 { 58 Q->front = NULL; 59 Q->rear = NULL; 60 } 61 62 //入队 63 void LQueueIn(Queue *Q, int data) 64 { 65 Qnode *pnew; //新节点 66 pnew = (Qnode *)malloc(sizeof(Qnode)); //开辟空间 67 pnew->data = data; //给新节点赋值 68 pnew->pnext = NULL; //把新节点的pnext指向空 69 70 //队尾 1、队尾节点有内容 2、原来的时候队尾啥也没有 71 if (Q->rear != NULL) 72 { 73 Q->rear->pnext = pnew; //1、队尾节点有内容 74 } 75 76 Q->rear = pnew; //2、原来的队尾啥也没有 77 78 if (Q->front == NULL) //front 有内容的时候 什么都不做 没有有内容的时候 79 { 80 Q->front = pnew; 81 } 82 } 83 84 85 //出队列 86 int LQueueOut(Queue *Q, int *data) 87 { 88 //malloc开辟的空间 释放 front改变掉 能不能找到我出去的节点 89 Qnode *pOut; 90 91 if (Q->front == NULL) 92 { 93 printf("队列空\n"); 94 return 0; 95 } 96 else 97 { 98 *data = Q->front->data; //把队头的数据赋值给data 99 pOut = Q->front; //先用临时指针pOut保存队头的数据 100 Q->front = Q->front->pnext; //把队头往后移动 //这里玩去能够知道front是不是空 101 102 if (Q->front == NULL) 103 { 104 Q->rear = NULL; 105 } 106 107 free(pOut); 108 return 1; 109 } 110 }
//动态存储
#include
malloc:动态开辟一块内存 (void *)malloc(size)
free();释放内存
calloc(): (void *)calloc(unsigned n,unsigned size);
在内存中动态开辟n个 大小为size的内存。存储空间是连续的。
realloc(): (void *)realloc(void *ptr,size_t size)
改变ptr这个指针所指向的内存空间的大小。
double *d=(double *)malloc(sizeof(double));
int *i;
i=realloc(d,sizeof(int));
总结:Void * 强制转换为任意的指针类型。
1 #include2 3 4 struct stu 5 { 6 int data; 7 struct stu *pnext 8 }; 9 10 11 int main() 12 { 13 struct stu *p; 14 p = (struct stu *)malloc(sizeof(struct stu)); 15 16 return 0; 17 }