#include <pthread.h>
#include <stdio.h>
#include <stdlib.h>
const int NUM = 20;
struct node
{
int val;
struct node *next;
};
void node_ini(struct node *n, int i)
{
n->val = i;
n->next = NULL;
}
void node_destroy(struct node *n)
{
free(n);
}
struct block_queue
{
struct node *head;
struct node *tail;
pthread_cond_t notempty; //非空条件变量
pthread_mutex_t mutex;
};
struct block_queue* block_queue_init()
{
struct block_queue * q = (struct block_queue*)malloc(sizeof(struct block_queue));
q->head = NULL;
q->tail = NULL;
pthread_cond_init(&q -> notempty, NULL);
pthread_mutex_init(&q -> mutex, NULL);
return q;
}
void block_queue_destroy(struct block_queue * q)
{
pthread_cond_destroy(&q->notempty);
pthread_mutex_destroy(&q->mutex);
free(q);
}
//尾部插入元素
void block_queue_push(struct block_queue *q, int i)
{
pthread_mutex_lock(&q->mutex);
struct node *n = (struct node*)malloc(sizeof(struct node));
node_ini(n, i);
if(q->tail == NULL)
{
q->tail = n;
}
else
{
q->tail->next = n;
q->tail = n;
}
if(q->head == NULL)
{
q->head = n;
}
pthread_mutex_unlock(&q->mutex);
//通知等待notempty的线程,队列不空
pthread_cond_signal(&q->notempty);
}
//头部取元素
int block_queue_pop(struct block_queue *q)
{
pthread_mutex_lock(&q->mutex);
while (q->head == NULL) {
printf("queue is empty, wait\n");
pthread_cond_wait(&q->notempty, &q->mutex);
}
struct node *p = q->head;
q->head = p->next;
pthread_mutex_unlock(&q->mutex);
int v = p->val;
free(p);
return v;
}
void* producer(void* args)
{
struct block_queue * queue = (struct block_queue *)args;
for (int i = 0; i < NUM; ++i) {
block_queue_push(queue, i);
printf("push:%d\n", i);
}
return NULL;
}
void* consumer(void* args)
{
struct block_queue * queue = (struct block_queue*)args;
for (int i = 0; i < NUM; ++i) {
int v = block_queue_pop(queue);
printf("pop:%d\n", v);
}
return NULL;
}
int main()
{
struct block_queue *queue = block_queue_init();
printf("Begin\n");
pthread_t pro_thread;
pthread_t con_thread;
pthread_create(&pro_thread, NULL, producer, queue);
pthread_create(&con_thread, NULL, consumer, queue);
pthread_join(pro_thread, NULL);
pthread_join(con_thread, NULL);
printf("End\n");
}