簡體   English   中英

從boost :: threads到boost :: asio定時器

[英]From boost::threads to boost::asio timers

在我的項目中,每個類對象都有自己的線程,內部有無限循環(while(1)),其中執行特定的對象函數。 而我正試圖改變這一點,以便每個對象都能與定時器異步執行其功能。

基本上這是它與無限循環的線程一起工作的方式:

class obj
{
    public:
          obj();
          ~obj();
         //custom functions and variables
        int x;
        int obj_action;
        move();
        wait();

}

obj()
{
     obj_action=1;
     //when constructing object, make its thread with infinite while cycle
     boost::thread make_thread(boost::bind(&obj::obj_engine,this));
}

void obj::obj_engine()
{
     while(true)
     {
       if (obj_action==1){move();}
       else if (obj_action==2){wait();}
       Sleep(1);
     }
}

void obj::move()
{
      x++;
      obj_action==2;
}


void obj::wait()
{
      Sleep(5000);
      obj_action==1;
}

這個例子顯示了obj類,它有構造函數,析構函數,幾個變量和幾個函數。 構造對象(obj())時,會創建線程。 Thread包含一個函數“obj_engine”,它具有無限循環(while(true))。 在循環中有兩個函數:1。wait() - 使線程休眠5秒。 2. walk() - 簡單地說x + 1這兩個函數在結束后通過定義obj_action來相互切換。

現在我想將此更改為,當構造和對象,異步move()函數將被執行時,並且在move()函數之后,將執行異步wait()函數,反之亦然。 所以我不需要使用任何線程。

我希望得到這樣的結果:

//constructing
obj()
{
       asynchronous(walk());
}

walk()
{
    x++
    asynchronous(wait());
}

wait()
{
    Sleep(5000);
    asynchronous(walk());
}

我聽說你可以用boost :: asio計時器做到這一點,但我真的不知道怎么做。 如果有人能告訴我如何,我將非常感激。

干得好:

#include <boost/asio.hpp>
#include <boost/date_time/posix_time/posix_time.hpp>
#include <boost/bind.hpp>
#include <iostream>



class obj {
public:
    obj() : x_(0), t_(io_service_, boost::posix_time::seconds(5)) {
        t_.async_wait(boost::bind(&obj::move, this));
        io_service_.run();
    }

    void move() {
        x_++;
        std::cout << x_ << std::endl;
        t_.expires_at(t_.expires_at() + boost::posix_time::seconds(5));
        t_.async_wait(boost::bind(&obj::move, this));
    }

private:
    int x_;
    boost::asio::io_service io_service_;
    boost::asio::deadline_timer t_;
};

int main(int, char**) {
    obj a;
    while(true);
}

基本上你需要的東西都包含在asio教程中: 本教程向你展示了如何使用異步計時器本教程將向你展示如何重置你的計時器

更新:

請使用上面的源代碼而不是我的初始代碼 - 由於io_service_.run()的重復調用,每個move調用都將在另一個線程中調用,並且一段時間之后您的應用程序將因此而崩潰。 上面的代碼解決了這個問題,並通過這樣做擺脫了wait函數。

借用nijansen的例子,我把一些應該更符合你想要的東西(我想)。

這里的關鍵是io_service應該在所有對象的調度之間共享。 通常每個線程有一個io_service,但也可以使用更復雜的方案。 只要io_service上有工作計划(掛起超時或等待套接字), io_service::run運行。 當不再安排工作時,它只會返回。

您可能對io_service::post感興趣,作為在“活動對象”之間發送消息的方式(即使它們在不同的io_services和不同的線程下運行,它也能工作)。 你可能想看看boost::bindboost::signals

#include <boost/asio.hpp>
#include <boost/date_time/posix_time/posix_time.hpp>
#include <boost/bind.hpp>
#include <iostream>

namespace asio = boost::asio;

class obj {
public:
    obj(asio::io_service& ioSvc)
      : x_(0), t_(ioSvc)
    {
        schedule_in(5);
    }

    void schedule_in(int seconds) {
        t_.expires_from_now(boost::posix_time::seconds(3));
        t_.async_wait(boost::bind(&obj::move, this));
    }

    void move() {
        x_++;
        std::cout << x_ << std::endl;
        schedule_in(5);
    }

private:
    int x_;
    boost::asio::deadline_timer t_;
};

int main(int, char**) {
    boost::asio::io_service io_service;
    obj a(io_service);
    obj b(io_service);
    obj c(io_service);
    io_service.run();
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM