zoukankan      html  css  js  c++  java
  • Linux 生产者消费者简单例子学习

    #if 0
        Linux实现生产者消费者模型
        1. 防止虚假唤醒
        2. 唤醒线程的时机很重要,否则会导致线程多次访问锁,影响性能
    #endif
    
    #include <unistd.h>
    #include <stdio.h>
    #include <iostream>
    #include <pthread.h>
    
    using namespace std;
    
    int g_value = 0;
    
    pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER;
    pthread_cond_t cond = PTHREAD_COND_INITIALIZER;
    
    void* consumer1(void* arg)
    {
        printf("consumer[%d] begin consume.
    ", (int)(*((int*)(arg))));
        pthread_mutex_lock(&mutex);
        printf("consumer[%d] pthread_mutex_lock.
    ", (int)(*((int*)(arg))));
        while (g_value <= 0) {//防止虚假唤醒
            printf("consumer[%d] begin wait.
    ", (int)(*((int*)(arg))));
            int ret = pthread_cond_wait(&cond, &mutex);
            if (ret) {
                printf("pthread_cond_wait error ret[%d].
    ", ret);
                return NULL;
            }
            printf("consumer[%d] end wait.
    ", (int)(*((int*)(arg))));
        }
        --g_value;
        printf("consumer[%d] g_value:[%d].
    ", (int)(*((int*)(arg))), g_value);
        pthread_mutex_unlock(&mutex);
        printf("consumer[%d] pthread_mutex_unlock.
    ", (int)(*((int*)(arg))));
        return NULL;
    }
    
    void* consumer2(void* arg)
    {
        printf("consumer[%d] begin consume.
    ", (int)(*((int*)(arg))));
        pthread_mutex_lock(&mutex);
        printf("consumer[%d] pthread_mutex_lock.
    ", (int)(*((int*)(arg))));
        while (g_value <= 0) {//防止虚假唤醒
            printf("consumer[%d] begin wait.
    ", (int)(*((int*)(arg))));
            int ret = pthread_cond_wait(&cond, &mutex);
            if (ret) {
                printf("pthread_cond_wait error ret[%d].
    ", ret);
                return NULL;
            }
            printf("consumer[%d] end wait.
    ", (int)(*((int*)(arg))));
        }
        --g_value;
        printf("consumer[%d] g_value:[%d].
    ", (int)(*((int*)(arg))), g_value);
        pthread_mutex_unlock(&mutex);
        printf("consumer[%d] pthread_mutex_unlock.
    ", (int)(*((int*)(arg))));
        return NULL;
    }
    
    void* producer(void* arg)
    {
        cout << "producer begin product." << endl;
        pthread_mutex_lock(&mutex);
        printf("producer pthread_mutex_lock.
    ");
        ++g_value;
        cout << "producer g_value: " << g_value << endl;
        if (g_value > 0) {
            cout << "producer begin pthread_cond_broadcast." << endl;
            int ret = pthread_cond_broadcast(&cond);
            if (ret) {
                printf("pthread_cond_broadcast error ret[%d].
    ", ret);
                return NULL;
            }
            cout << "producer end pthread_cond_broadcast." << endl;
        }
        printf("producer begin pthread_mutex_unlock.
    ");
        int ret = pthread_mutex_unlock(&mutex);
        if (ret) {
            printf("pthread_mutex_unlock error ret[%d].
    ", ret);
            return NULL;
        }
        printf("producer end pthread_mutex_unlock.
    ");
        return NULL;
    }
    
    int join(pthread_t tid, void **retval)
    {
        int ret = pthread_join(tid, retval);
        if (ret) {
            return ret;
        }
        else {
            return 0;
        }
    }
    
    int main()
    {
        pthread_t tid_consumer[2] = {0};
        pthread_t tid_producer = 0;
        int ret = -1;
        int _consumer1 = 1;
        ret = pthread_create(&tid_consumer[0], NULL, &consumer1, (void*)(&_consumer1));
        if (ret) {
            printf("pthread_create error ret[%d].
    ", ret);
            return -1;
        }
        sleep(1);
        int _consumer2 = 2;
        ret = pthread_create(&tid_consumer[1], NULL, &consumer2, (void*)(&_consumer2));
        if (ret) {
            printf("pthread_create error ret[%d].
    ", ret);
            return -1;
        }
    
        sleep(5);
        ret = pthread_create(&tid_producer, NULL, &producer, NULL);
        if (ret)
        {
            printf("pthread_create error ret[%d].
    ", ret);
            return -1;
        }
        sleep(2);
    
        for (int i = 0; i < sizeof(tid_consumer)/sizeof(tid_consumer[0]); ++i)
        {
            ret = join(tid_consumer[i], NULL);
            if (ret) {
                printf("join error ret[%d].
    ", ret);
            }
        }
        ret = join(tid_producer, NULL);
        if (ret) {
            printf("join error ret[%d].
    ", ret);
            return -1;
        }
        printf("pthread join success.
    ");
    
        return 0;
    }
  • 相关阅读:
    javascript中万恶的function
    Windows7下如何安装部署秋色园CYQBlog源码V1.0网站
    Extjs2.2:Panel里面嵌入Excel表格
    Extjs做界面很酷;感谢博客园给我一个展示的机会;借此向大家展示一下EXTJS的魅力
    16Aspx.com改进版Extjs简单版酒店管理系统提供下载!
    Ext2.2+ASP.NET开发框架已完成欢迎大家下载!
    Extj+Asp.net开发框架V1.1树的操作
    Ext2.2程序开发实战(1)登录界面
    扩展欧几里得定理
    C语言 统计整数二进制表示中1的个数
  • 原文地址:https://www.cnblogs.com/chen-cai/p/11382643.html
Copyright © 2011-2022 走看看