Tho*_*ann 4 c++ networking boost tcp boost-asio
在使用async_read和async_write时,我很难理解构建tcp客户端的正确方法.的例子似乎做一个async_read连接后,然后在处理程序ASYNC_WRITE.
在我的客户端和服务器的情况下,当客户端连接时,它需要检查要写入的消息队列并检查是否需要读取任何内容.我遇到困难的一件事就是了解这将如何异步工作.
我想象的是在async_connect处理程序中,如果sendQueue中有任何内容并且反复调用async_read,则线程将调用async_write.或者它应该检查在执行async_read之前是否有可读的内容?以下是我所说的一个例子.
void BoostTCPConnection::connectHandler()
{
setRunning(true);
while (isRunning())
{
//If send Queue has messages
if ( sendSize > 0)
{
//Calls to async_write
send();
}
boost::shared_ptr<std::vector<char> > sizeBuffer(new std::vector<char>(4));
boost::asio::async_read(socket_, boost::asio::buffer(data, size), boost::bind(&BoostTCPConnection::handleReceive, shared_from_this(), boost::asio::placeholders::error, sizeBuffer));
}
}
void BoostTCPConnection::handleReceive(const boost::system::error_code& error, boost::shared_ptr<std::vector<char> > sizeBuffer)
{
if (error)
{
//Handle Error
return;
}
size_t messageSize(0);
memcpy((void*)(&messageSize),(void*)sizeBuffer.data(),4);
boost::shared_ptr<std::vector<char> > message(new std::vector<char>(messageSize) );
//Will this create a race condition with other reads?
//Should a regular read happen here
boost::asio::async_read(socket_, boost::asio::buffer(data, size),
boost::bind(&BoostTCPConnection::handleReceiveMessage, shared_from_this(),
boost::asio::placeholders::error, message));
}
void BoostTCPConnection::handleReceiveMessage(const boost::system::error_code& error, boost::shared_ptr<std::vector<char> > rcvBuffer)
{
if (error)
{
//Handle Error
return;
}
boost::shared_ptr<std::string> message(new std::string(rcvBuffer.begin(),rcvBuffer.end()));
receivedMsgs_.push_back(message);
}
void BoostTCPConnection::handleWrite(const boost::system::error_code& error,size_t bytes_transferred)
{
//Success
if (error.value() == 0)
return;
//else handleError
}
Run Code Online (Sandbox Code Playgroud)
从概念上讲,async_read等待接收数据.在收到数据并且读取尚未处理之后,您应该随时调用它.同样,async_write等待写入数据.您应该在需要写入数据时调用它,并且写入尚未处于待处理状态.
async_read完成连接后应该打电话.在async_read处理程序返回之前,它可能应该async_read再次调用.
当您需要写入连接时,您应该调用async_write(如果写入尚未挂起).在你的async_write处理程序中,如果你还需要写更多,你应该async_write再次打电话.
如果没有待处理的读取,则可以async_read在写入处理程序中调用,如果您希望在完成写入后继续读取.您也可以保持读取始终挂起.随你(由你决定.
在打电话之前,你不应该检查是否有任何东西要读async_read.关键async_read是要在有东西要读的时候完成.在此期间,这是一种等待和做其他事情的聪明方式.
| 归档时间: |
|
| 查看次数: |
1482 次 |
| 最近记录: |