ACE_Message_Queue和spawn实现(生产者/消费者)(V2.00)

ACE_Message_Queue和spawn实现(生产者/消费者)(V2.00)

大家好,又见面了,我是全栈君。

參考这里用到了线程管理。參考:http://blog.csdn.net/calmreason/article/details/36399697

以下的两个线程共享一个消息队列,一个用来放整数到队列,一个从队列里取消息出来。

此程序在控制台不停的输出递增数字,主要是内存不会泄露

用到了多线程、ACE_Message_Queue、ACE_Message_Block、ACE_Thread_Manager::instance()->spawn等

#include <iostream>
using namespace std;
#include "boost/lexical_cast.hpp"
using namespace boost;
#include "ace/Thread_Manager.h" 
#include "ace/Message_Queue.h"

void* create_vairous_record(void* ace_message_queue);

void* get_vairous_record(void* ace_message_queue);

int ACE_TMAIN (int argc, ACE_TCHAR *argv[]) 
{

	ACE_Message_Queue<ACE_MT_SYNCH>* various_record_queue = new ACE_Message_Queue<ACE_MT_SYNCH>;

	ACE_Thread_Manager::instance()->spawn(
		ACE_THR_FUNC(create_vairous_record), 
		various_record_queue, 
		THR_NEW_LWP | THR_DETACHED);

	ACE_Thread_Manager::instance()->spawn(
		ACE_THR_FUNC(get_vairous_record), 
		various_record_queue, 
		THR_NEW_LWP | THR_DETACHED);

	ACE_Thread_Manager::instance()->wait();

	return 0;
}

void* create_vairous_record(void* ace_message_queue)
{

	ACE_Message_Queue<ACE_MT_SYNCH>* p_queue = (ACE_Message_Queue<ACE_MT_SYNCH>*)ace_message_queue;
	int i=0;
	while (i<10000000)
	{
		ACE_Message_Block* mbl = new ACE_Message_Block(10);//在这里创建消息
		string temp = lexical_cast<string>(++i);
		mbl->copy(temp.c_str());
		p_queue->enqueue_tail(mbl);//消息被放到队列中(用指针引用消息实体)
	}
	return nullptr;
}

void* get_vairous_record(void* ace_message_queue)
{

	ACE_Message_Queue<ACE_MT_SYNCH>* p_queue = (ACE_Message_Queue<ACE_MT_SYNCH>*)ace_message_queue;
	while (true)
	{
		ACE_Message_Block* mbl =nullptr;
		p_queue->dequeue_head(mbl);//消息出队,出队的消息应该在用完之后被释放
		if (mbl)
		{
			cout<<mbl->rd_ptr()<<endl;
			mbl->release();//消息已经用完。释放消息
		}
	}
	return nullptr;

}

以下的程序实现:多个线程将连续整数分批放到ACE_Message_Queue中,一个消费者线程负责从中取出,并验证数据是否完整无误

#include <iostream>
#include <bitset>
#include <vector>
#include <memory>
using namespace std;

#include "ace/Thread_Manager.h" 
#include "ace/Message_Queue.h"
#include "ace/Message_Block.h"
#include "ace/Task.h"
#include "ace/OS.h"

namespace global
{
    const int total_number = 1000000;
    int task_number = 2;
    typedef int number_type;
}

class Generator_Number : public ACE_Task<ACE_MT_SYNCH>
{
public:
    Generator_Number(ACE_Message_Queue<ACE_MT_SYNCH>* msgq,const int i);
    virtual int open(void *args  = 0 );
    ~Generator_Number(void);
protected:
    Generator_Number(const Generator_Number&);
    Generator_Number& operator=(const Generator_Number&);
private:
    int svc(void);
    int mod_i_;
};

Generator_Number::Generator_Number(ACE_Message_Queue<ACE_MT_SYNCH>* msgq,const int i):mod_i_(i)
{
    this->msg_queue(msgq);
    std::cout<<"Generator_Number(const int "<<i<<")"<<std::endl;
}

int Generator_Number::open(void *args )
{
    return this->activate(THR_NEW_LWP | THR_DETACHED);
}

int Generator_Number::svc(void)
{
    std::cout<<"Generator_Number("<<this->mod_i_<<")::svc()"<<std::endl;
    for (size_t i = this->mod_i_ ; i<global::total_number;i+=global::task_number)
    {
        ACE_Message_Block * blk = new ACE_Message_Block(20);
        blk->copy(reinterpret_cast<const char*>(&i),sizeof(global::number_type));
        this->msg_queue()->enqueue_tail(blk);
    }
    return 0;
}

Generator_Number::~Generator_Number(void)
{
    std::cout<<"~Generator_Number("<<this->mod_i_<<")"<<std::endl;
}

void* out_put_queue(void* all_numbers_queue1)
{
    ACE_Message_Queue<ACE_MT_SYNCH>* all_numbers_queue = (ACE_Message_Queue<ACE_MT_SYNCH>*)all_numbers_queue1;
    bitset<global::total_number> all_number_bitset;
    size_t count_got_message=0;
    while(true)
    {
        if(!all_numbers_queue->is_empty())
        {
            ACE_Message_Block* blk = 0;
            all_numbers_queue->dequeue_head(blk);
            all_number_bitset.set(*reinterpret_cast<global::number_type*>(blk->rd_ptr()));
            blk->release();
            if(++count_got_message == global::total_number)
            {
                break;
            }
        }
        else
        {
            std::cout<<"now sleep 1"<<std::endl;
            ACE_Time_Value t(0,3000);
            ACE_OS::sleep(t);
        }
    }
    global::number_type check =0;
    bool wright_flag = true;
    for (size_t j=0; j!= global::total_number;++j)
    {
        if (0 == all_number_bitset[j])
        {
            wright_flag = false;
            break;
        }
    }
    std::cout<<std::endl;
    std::cout<<"check result:"<<wright_flag<<std::endl;
    return 0;
}
#include "boost/timer.hpp"
using namespace boost;

int ACE_TMAIN (int argc, ACE_TCHAR *argv[]) 
{
    cout<<"total_number:"<<global::total_number<<endl;
    timer t;
    ACE_Message_Queue<ACE_MT_SYNCH>* all_numbers_queue = new ACE_Message_Queue<ACE_MT_SYNCH>;

    vector<shared_ptr<Generator_Number>> gener_array;

    for (int i=0;i<global::task_number;++i)
    {
        gener_array.push_back(shared_ptr<Generator_Number>(new Generator_Number(all_numbers_queue,i)));
    }
    for (vector<shared_ptr<Generator_Number>>::const_iterator citer = gener_array.cbegin();
        citer!=gener_array.cend();
        ++citer)
    {
        (*citer)->open();
    }

    ACE_Thread_Manager::instance()->spawn(
        ACE_THR_FUNC(out_put_queue),   
        all_numbers_queue,   
        THR_NEW_LWP | THR_DETACHED);

    ACE_Thread_Manager::instance()->wait();
    cout<<t.elapsed()<<"s"<<endl;
    return 0;
}


输出例如以下:

total_number:1000000
Generator_Number(const int 0)
Generator_Number(const int 1)
Generator_Number(0)::svc()
Generator_Number(1now sleep 1
)::svc()
now sleep 1
now sleep 1
now sleep 1
now sleep 1
now sleep 1
now sleep 1
now sleep 1
now sleep 1
now sleep 1

check result:1
0.944s
~Generator_Number(0)
~Generator_Number(1)
请按随意键继续. . .

ACE_Message_Queue

高水位低水位

http://blog.163.com/ecy_fu/blog/static/4445126200964115620862/

注意事项

http://blog.chinaunix.net/uid-20453737-id-37118.html

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请联系我们举报,一经查实,本站将立刻删除。

发布者:全栈程序员-站长,转载请注明出处:https://javaforall.net/115237.html原文链接:https://javaforall.net

(0)
全栈程序员-站长的头像全栈程序员-站长


相关推荐

  • 约瑟夫环问题详解

    约瑟夫环问题详解在牛客网上做到一道题,是约瑟夫环的变型,所以借此学习一下新知识,并且巩固一下对题目意思的理解,这一篇仅作约瑟夫环问题的解释,下一篇再写题目:1.首先,我们先来了解一下什么是约瑟夫环问题:讲一个比较有意思的故事:约瑟夫是犹太军队的一个将军,在反抗罗马的起义中,他所率领的军队被击溃,只剩下残余的部队40余人,他们都是宁死不屈的人,所以不愿投降做叛徒。一群人表决说要死,所以用一种策略来先后杀…

    2022年6月4日
    31
  • PyCharm配置教程[通俗易懂]

    PyCharm配置教程[通俗易懂]一、安装进入pyCharm官网:https://www.jetbrains.com/pycharm。根据自己的操作系统选择相应的下载包。其中专业版是要付费的,可以自行购买,也可以google搜索激活成功教程教程。下载后根据提示安装即可二、配置1.设置主题以及字体大小点击PyCharm,进入preferences选项设置更改主题以及字体颜色2.配置属于自己的文件模板举个例子,如果你要创建一个python文件,那么你可能需要类似这样的代码注释在文件的最上方文件代码注释如果我们

    2022年8月26日
    8
  • TranslateMessage ,GetMessage, DispatchMessage分析

    TranslateMessage ,GetMessage, DispatchMessage分析TranslateMessage(&msg);TranslateMessage是用来把快捷键消息转换为字符消息,并将转换后的新消息投递到调用线程的消息队列中。由于Windows对所有键盘编码都是采用虚拟键的定义,这样当按键按下时,并不得字符消息,需要键盘映射转换为字符的消息。字符消息被投递到调用线程的消息队列中,当下一次调用GetMessage函数时被取出。LONGDispatchMessage(CONSTMSG*lpmsg);函数功能:该函数分发一个消息给窗口程序,即把消息推送

    2022年9月13日
    0
  • 渗透测试工具——漏洞扫描工具

    渗透测试工具——漏洞扫描工具安全漏洞产生的原因技术原因软件系统复杂性提高,质量难于控制,安全性降低 公用模块的使用引发了安全问题经济原因“柠檬市场”效应——安全功能是最容易删减的部分环境原因从传统的封闭、静态和可控变为开放、动态和难控 攻易守难安全缺陷安全性缺陷是信息系统或产品自身“与生俱来”的特征,是其“固有成分”安全漏洞是与生俱来的系统设计缺陷Internet从设计时就缺乏安全的总体架构和设计 TCP/IP中的三阶段握手.软件源代码的急剧膨胀Windows951500万行

    2022年9月13日
    0
  • Spring IOC 之解析 bean 标签:开启解析进程,BeanDefinition

    Spring IOC 之解析 bean 标签:开启解析进程,BeanDefinitionSpring IOC 之解析 bean 标签:开启解析进程,BeanDefinition

    2022年4月20日
    50
  • java权限管理面试_java shiro面试题

    java权限管理面试_java shiro面试题1、简单介绍一下Shiro框架?ApacheShiro是Java的一个安全框架。使用Shiro可以非常容易的开发出足够好的应用。其不仅可以用在JavaSE环境,也可以用在JavaEE环境。Shiro可以帮助我们完成功能:认证、授权、加密、会话管理、与Web集成、缓存等。三个核心组件:Subject,SecurityManager和Realms。●Subject:即“当前操作用户”。但是在Shi…

    2022年10月14日
    0

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注

关注全栈程序员社区公众号