1.概念
队列:
队列是只允许在一段进行插入,而在另一端进行删除操作的线性表。
允许插入的称谓队尾,允许删除的一端队头。
顺序队列。
循环队列,
常用操作,入队,出队。
先进先出,FIFO(有名管道)
判断空、满:
空:头==尾
满:尾 + 1==头
哪些地方会用到队列:
多线程、多进程 读写速率不匹配,输入输出速率不匹配,需要缓冲区的,提高效率
2.顺序结构
seqque.h
#ifndef _SEQQUE_H_
#define _SEQQUE_H_
typedef int DATATYPE;
typedef struct {
DATATYPE *array;
int tlen;
int head;
int tail;
}SeqQueue;
SeqQueue *CreateSeqQueue(int len);
int DestroySeqQueue(SeqQueue *queue);
int QuitSeqQueue(SeqQueue *queue);
int EnterSeqQueue(SeqQueue *queue, DATATYPE *data);
int IsEmptySeqQueue(SeqQueue *queue);
int IsFullSeqQueue(SeqQueue *queue);
DATATYPE* GetHeadSeqQueue(SeqQueue* queue);
#endif
seqque.c
#include "seqque.h"
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
SeqQueue *CreateSeqQueue(int len)
{
SeqQueue* sq =(SeqQueue*)malloc(sizeof(SeqQueue));
if(NULL == sq)
{
perror("CreateSeqQueue malloc");
return NULL;
}
sq->array = (DATATYPE*)malloc(sizeof(DATATYPE)*len);
if(NULL == sq->array)
{
perror("CreateSeqQueue");
return NULL;
}
sq->tlen = len;
sq->head = 0 ;
sq->tail = 0 ;
return sq;
}
int DestroySeqQueue(SeqQueue *queue)
{
return 0;
}
int QuitSeqQueue(SeqQueue *queue)
{
if(IsEmptySeqQueue(queue))
{
return 1;
}
queue->head = (queue->head +1)%queue->tlen ;
return 0;
}
int EnterSeqQueue(SeqQueue *queue, DATATYPE *data)
{
if(IsFullSeqQueue(queue))
{
return 1;
}
memcpy(&queue->array[queue->tail],data,sizeof(DATATYPE));
queue->tail = (queue->tail +1)%queue->tlen;
return 0;
}
int IsEmptySeqQueue(SeqQueue *queue)
{
return queue->head == queue->tail ;
}
int IsFullSeqQueue(SeqQueue *queue)
{
return (queue->tail +1 )%queue->tlen == queue->head ;
}
DATATYPE* GetHeadSeqQueue(SeqQueue* queue)
{
if(IsEmptySeqQueue(queue)) return NULL;
return &queue->array [queue->head];
}
main.c
#include "seqque.h"
#include <stdio.h>
int main(int argc, char *argv[])
{
SeqQueue* sq = CreateSeqQueue(5);
int i =0 ;
for(i = 0;i<5;i++)
{
EnterSeqQueue(sq,&i);
}
while(!IsEmptySeqQueue(sq))
{
DATATYPE*tmp = GetHeadSeqQueue(sq);
printf("%d\n",*tmp);
QuitSeqQueue(sq);
}
DestroySeqQueue(sq);
return 0;
}
练习
用线程
{"cooking", 5},
{"washing", 3},
{"working", 8},
{"playing", 5},
{"over",0},
#include "seqque.h"
#include <pthread.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <semaphore.h>
#include <unistd.h>
sem_t sem_task;
void* th1(void* arg)
{
SeqQueue* sq =(SeqQueue*) arg;
DATATYPE data;
while(1)
{
bzero(&data,sizeof(data));
sem_wait(&sem_task);
DATATYPE* tmp = GetHeadSeqQueue(sq);
memcpy(&data,tmp,sizeof(DATATYPE));
QuitSeqQueue(sq);
if(0 == strcmp(data.task_name ,"over"))
{
break;
}
while(data.task_time--)
{
printf("I'm %s\n",data.task_name);
sleep(1);
}
}
return NULL;
}
int main(int argc, char *argv[])
{
DATATYPE data []=
{
{"cooking", 5},
{"washing", 3},
{"working", 8},
{"playing", 5},
{"over",0},
};
SeqQueue* sq = CreateSeqQueue(10);
pthread_t tid1;
sem_init(&sem_task,0,0);
pthread_create(&tid1,NULL,th1,sq);
DATATYPE dat;
while(1)
{
bzero(&dat,sizeof(dat));
char buf[5]={0};// 1 2 3 4 5\n
int num = 0 ;
fgets(buf,sizeof(buf),stdin);
num = atoi(buf);
//dat = data[num-1];
memcpy(&dat,&data[num-1],sizeof(DATATYPE));
EnterSeqQueue(sq,&dat);
sem_post(&sem_task);
if(0 ==strcmp(dat.task_name ,"over"))
{
break;
}
}
pthread_join(tid1,NULL);
sem_destroy(&sem_task);
DestroySeqQueue(sq);
return 0;
}
3.链式队列
linkqueue.h
#ifndef _LINKQUEUE_H_
#define _LINKQUEUE_H_
typedef int DATATYPE;
typedef struct link_que_node {
DATATYPE data;
struct link_que_node *next;
}QueueNode;
typedef struct {
QueueNode *head;
int clen;
QueueNode *tail;
}LinkQueue;
LinkQueue *CreateLinkQueue();
int DestroyLinkQueue(LinkQueue *queue);
int QuitLinkQueue(LinkQueue *queue);
DATATYPE* GetHeadLinkQue(LinkQueue*queue);
int EnterLinkQueue(LinkQueue *queue, DATATYPE *data);
int IsEmptyLinkQueue(LinkQueue *queue);
#endif
linkqueue.c
#include "linkqueue.h"
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
LinkQueue *CreateLinkQueue()
{
LinkQueue* lq = (LinkQueue*)malloc(sizeof(LinkQueue));
if(NULL == lq)
{
perror("CreateLinkQueue malloc");
return NULL;
}
lq->head = NULL;
lq->tail = NULL;
lq->clen = 0;
return lq;
}
int DestroyLinkQueue(LinkQueue *queue)
{
while(!IsEmptyLinkQueue(queue))
{
QuitLinkQueue(queue);
}
free(queue);
return 0;
}
int QuitLinkQueue(LinkQueue *queue)
{
if(IsEmptyLinkQueue(queue))
{
return 1;
}
QueueNode* tmp = queue ->head ;
queue->head = queue->head->next ;
free(tmp);
queue->clen --;
if(NULL == queue->head )
{
queue->tail = NULL;
}
return 0;
}
DATATYPE* GetHeadLinkQue(LinkQueue*queue)
{
if(IsEmptyLinkQueue(queue))
{
return NULL;
}
return &queue->head->data;
}
int EnterLinkQueue(LinkQueue *queue, DATATYPE *data)
{
QueueNode* newnode =(QueueNode*)malloc(sizeof(QueueNode));
if(NULL == newnode)
{
perror("EnterLinkQueue malloc");
return 1;
}
memcpy(&newnode->data,data,sizeof(DATATYPE));
newnode->next = NULL;
if(IsEmptyLinkQueue(queue))
{
queue->head = newnode;
queue->tail = newnode;
}
else
{
queue->tail->next = newnode;
queue->tail = newnode;
}
queue->clen ++;
return 0;
}
int IsEmptyLinkQueue(LinkQueue *queue)
{
return 0 == queue->clen;
}
main.c
#include "linkqueue.h"
#include <string.h>
#include <stdio.h>
int main(int argc, char *argv[])
{
LinkQueue*lq = CreateLinkQueue();
int i = 0;
for(i = 0 ;i<10;i++)
{
EnterLinkQueue(lq,&i);
}
DATATYPE data;
while(!IsEmptyLinkQueue(lq))
{
DATATYPE*ret = GetHeadLinkQue(lq);
memcpy(&data,ret,sizeof(DATATYPE));
QuitLinkQueue(lq);
printf("%d\n",data);
}
DestroyLinkQueue(lq);
return 0;
}