Boost Asio-为什么我的异步操作没有启动

Boost Asio - Why do my asynchronous operations not launch?

本文关键字:启动 异步操作 我的 Asio- 为什么 Boost      更新时间:2023-10-16

我最近遇到了一个关于boost::asio异步任务的问题。我想在侦听端口的对象上返回一个指针。当我使用socket.read_some方法时,它可以工作,但这个方法阻塞了我的main,我希望我的MyClass::create方法返回。

所以我尝试了一个async_read调用,但我发现在read()方法中,没有启动异步任务。我试图找出问题的原因,但没有找到解决这个问题的办法。

这是我的代码,这里不是async_read,而是async_wait,同样的问题出现了,计时器没有启动。

谢谢你给我的任何帮助。

头文件:

#ifndef MYCLASS_HPP
#define MYCLASS_HPP
#include <memory>
#include <boost/asio.hpp>
class MyClass
{
public:
MyClass(boost::asio::io_service& ios);
void read();
void read_handler(const boost::system::error_code& error);
static std::shared_ptr<MyClass> create(std:: string const & host, uint16_t port);
bool connect (std::string const & host, uint16_t port);
void connect_handler(const boost::system::error_code& error);

boost::asio::ip::tcp::socket    m_socket;
bool                m_flag;
std::vector<uint8_t>        m_buffer;   
};
#endif

源文件:

#include "MyClass.hpp"
#include <boost/bind.hpp>
MyClass::MyClass(boost::asio::io_service& ios)
    :m_flag(false), m_socket(ios), m_buffer(20)
{   
}
void MyClass::read_handler(const boost::system::error_code& er)
{
    std::cout << "Timer waited 5 sec" << std::endl;
}

void MyClass::read()
{
    boost::asio::deadline_timer t(m_socket.get_io_service(),boost::posix_time::seconds(5));
    t.async_wait(boost::bind(&MyClass::read_handler,this,boost::asio::placeholders::error));
    m_socket.get_io_service().run();//Should make the io_service wait for all asynchronous tasks to finish
    std::cout << "This message should be displayed after the wait" << std::endl;
}
void MyClass::connect_handler(const boost::system::error_code& error)
{
    if(!error)
    {
        std::cout << "Connection done" << std::endl;
        m_flag = 1; 
    }
    else 
    {
        std::cout << "Error in connection: " << error.message() << std::endl;
    }
}

//connect method
bool MyClass::connect(std::string const & host, uint16_t port)
{
    boost::asio::ip::tcp::endpoint endpoint(boost::asio::ip::address::from_string(host),port);
    m_socket.async_connect(endpoint, 
            boost::bind(&MyClass::connect_handler, this,
            boost::asio::placeholders::error));
    m_socket.get_io_service().run();//Wait async_connect and connect_handler to finish
    if (m_flag == 0) return false;
    else return true;
}

std::shared_ptr<MyClass> MyClass::create(std:: string const & host, uint16_t port)
{
    boost::asio::io_service ios;
    std::shared_ptr<MyClass> ptr(new MyClass(ios));
    bool bol = ptr->connect(host, port);
    ptr->read();
    //while(1){}
    if(bol == true)
    {
        //connection success, reading currently listening, pointer is returned to the user
        return ptr;
    }
    else
    {
        //connection failure, pointer is still returned to the user but not listening as he's not connected
        return ptr;
    }
}

我的主要:

#include <boost/date_time/posix_time/posix_time.hpp>
#include <boost/asio.hpp>
#include "MyClass.hpp"
int main()
{
    try
    {
    std::cout << "Creation of instance" << std::endl;
    std::shared_ptr <MyClass> var = MyClass::create("127.0.0.1", 8301);
    std::cout << "Instance created" << std::endl;

    }
    catch (std::exception& e)
    {
        std::cerr << e.what() << std::endl;
    }
    return 0;
}

我想好了如何解决我的问题。

我确实遇到了io_service在"create"方法后被破坏的问题,所以在main中返回的指针无法继续读取。有一次我不得不调用run()来启动回调,但我不能在main中执行,因为我希望main继续做其他事情。

因此,我创建了一个类,启动一个独立的线程,并包含一个io_service。该线程正在周期性地调用run()。然后将其作为属性添加到MyClass中。

现在,我调用了"create",返回一个指向MyClass的指针,该指针不会停止在MyClass中启动的任何异步任务。