码迷,mamicode.com
首页 > 其他好文 > 详细

生产者消费者之关于boost::condition的用法

时间:2015-05-07 12:19:37      阅读:151      评论:0      收藏:0      [点我收藏+]

标签:

boost线程库的基本用法这篇文章有介绍到
http://www.cppblog.com/fwxjj/archive/2006/12/04/15975.html

我这里只讨论boost::condition在reader/writer模式中的一些注意点

首先我们看只有一个reader/一个writer的情形

#include <boost/thread/mutex.hpp>
#include <boost/thread/condition.hpp>
#include <boost/thread/thread.hpp>
#include <boost/thread/xtime.hpp>
#include <iostream>

int number;
boost::mutex m;
boost::condition not_full;
boost::condition not_empty;

void writer()
{
    while (1) {
        boost::mutex::scoped_lock sl(m);
        if (number == 5) {
            not_full.wait(m);
        }
        ++number;
        std::cout << "after w: " << number << std::endl;
        not_empty.notify_one();
    }
}

void reader()
{
    while (1) {
        boost::mutex::scoped_lock sl(m);
        if (number == 0) {
            not_empty.wait(m);       
        }
        --number;
        std::cout << "after r: " << number << std::endl;
        not_full.notify_one();
    }
}

void main()
{
    boost::thread trd1(&writer);
    boost::thread trd2(&reader);
    trd1.join();
    trd2.join();
}


运行之后程序一切如常,0-5的一些数字会打印出来。

但是当另外一个write加入战局的时候,情况变得有些微妙的不同,如果我们只是在main里面加入一个writer,其他部分保持不变的话,你会看到一些错误的数字出现:

void main()
{
    boost::thread trd1(&writer);
    boost::thread trd11(&writer);
    boost::thread trd2(&reader);
    trd1.join();
    trd11.join();
    trd2.join();
}


究其原因是:在reader->notify_one之后并在socped_lock解锁之前,在not_full上等待的writer A被唤起,然后reader解锁,此时可能另外一个writer B先获得锁而直接增加了number。在writeB 解锁后, writerA获得锁,但此时not_full条件已经被破坏。所以一种做法是再次检查该条件,也就是这样:

while (number == 5) {
    not_full.wait(m);
}


对于多write或多reader的情形也是一样都需要以一个while循环进行conditiond的复检:完整的代码如下

#include <boost/thread/mutex.hpp>
#include <boost/thread/condition.hpp>
#include <boost/thread/thread.hpp>
#include <boost/thread/xtime.hpp>
#include <iostream>

int number;
boost::mutex m;
boost::condition not_full;
boost::condition not_empty;

void writer()
{
    while (1) {
        boost::mutex::scoped_lock sl(m);
        while (number == 5) {
            not_full.wait(m);
        }
        ++number;
        std::cout << "after w: " << number << std::endl;
        not_empty.notify_one();
    }
}

void reader()
{
    while (1) {
        boost::mutex::scoped_lock sl(m);
        while (number == 0) {
            not_empty.wait(m);       
        }
        --number;
        std::cout << "after r: " << number << std::endl;
        not_full.notify_one();
    }
}

void main()
{
    boost::thread trd1(&writer);
    boost::thread trd11(&writer);
    boost::thread trd2(&reader);
    boost::thread trd22(&reader);
    trd1.join();
    trd11.join();
    trd2.join();
    trd22.join();
}

生产者消费者之关于boost::condition的用法

标签:

原文地址:http://www.cnblogs.com/txf1949/p/4484106.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!