zoukankan      html  css  js  c++  java
  • 简单的生产-消费者程序

     1 #include <stdlib.h>
     2 #include <pthread.h>
     3 #include <stdio.h>
     4 #include <sys/unistd.h>
     5 
     6 #define PRINT_LINE  printf("FILE: %s,  LINE: %d
    ", __FILE__, __LINE__);
     7 #define CYCLE_TIME  (5)
     8 typedef struct msg {
     9     struct msg *prev;
    10     struct msg *next;
    11     int num;
    12 } *pMsg;
    13 
    14 pMsg head;
    15 pMsg tail;
    16 pthread_cond_t has_product = PTHREAD_COND_INITIALIZER;
    17 pthread_mutex_t lock = PTHREAD_MUTEX_INITIALIZER;
    18 void printList();
    19 void *consumer(void *p)
    20 {
    21     struct msg *mp = NULL;
    22     for (;;) {
    23     pthread_mutex_lock(&lock);
    24     while (head == NULL && tail == NULL) {
    25         printf("head is: %p, tail is: %p
    ", head, tail);
    26         pthread_cond_wait(&has_product, &lock);
    27     }
    28     //printList();
    29     mp = tail;
    30     //if tail point the first Node, tail->next is NULL, and tail->prev is also NULL!
    31     //So, in this condition, tail point to NULL after statement "tail = tail->prev;"
    32     //this happened before second node is produced, because consumer get the lock
    33     tail = tail->prev;
    34     if (tail) {//tail not point to first
    35         tail->next = NULL;
    36     }
    37     else //tail point to first, so after consume node, List is EMPTY!
    38         head = NULL;//init List to NULL, so producer will add the next node to 
    39                     //List and arise tail to it, add consumer will wait until List is Not EMPTY.
    40     pthread_mutex_unlock(&lock);
    41     printf("Consume	%d
    ", mp->num);
    42     free(mp);        //PRINT_LINE
    43     sleep(rand() % CYCLE_TIME);
    44     }
    45 }
    46 
    47 void *producer(void *p)
    48 {
    49     struct msg *mp;
    50     for (;;) {
    51     mp = malloc(sizeof(struct msg));
    52     mp->num = rand() % 1000 + 1;
    53     printf("Produce	%d
    ", mp->num);
    54     pthread_mutex_lock(&lock);
    55     mp->prev = NULL;
    56     mp->next = head;
    57     if (tail == NULL) {    //if the first Node is consumed
    58         //before the second node is produced,
    59         //this statement arise tail to second node.
    60         tail = mp;
    61     }
    62     if (head)
    63         head->prev = mp;
    64     head = mp;
    65     //printList();
    66     pthread_mutex_unlock(&lock);
    67     pthread_cond_signal(&has_product);
    68 
    69     sleep(rand() % CYCLE_TIME);
    70     }
    71 }
    72 
    73 int main(int argc, char *argv[])
    74 {
    75     head = tail = NULL;
    76     pthread_t pid, cid;
    77     srand(time(NULL));
    78     pthread_create(&pid, NULL, producer, NULL);
    79     pthread_create(&cid, NULL, consumer, NULL);
    80     pthread_join(pid, NULL);
    81     pthread_join(cid, NULL);
    82     return 0;
    83 }
    84 
    85 void printList()
    86 {
    87     pMsg mp=NULL;
    88     printf("------------List Start ----------
    ");
    89     mp = head;
    90     while (mp) {
    91     printf
    92         ("element: mp - %p, mp->prev - %p, mp->num - %d, mp->next - %p;
    ",
    93          mp, mp->prev, mp->num, mp->next);
    94     printf("head: %p, tail: %p
    ", head, tail);
    95     mp = mp->next;
    96     }
    97     printf("------------List End ----------
    ");
    98 }

    参考的<<Linux C 一站式编程>> "第35章 线程 第3节 线程同步"的代码和习题

  • 相关阅读:
    docker运行springboot应用
    docer运行node
    Git添加仓库
    安装docker-compose
    centos安装docker
    Centos设置软件源
    ubuntu安装docker
    ubuntu安装阿里云镜像地址
    docker加速器配置
    配置Spring发送邮件
  • 原文地址:https://www.cnblogs.com/freudshow/p/5159389.html
Copyright © 2011-2022 走看看