Boost.Asio c++ 网络编程翻译(10)
read/write方法
这些方法对一个流进行读写操作(能够是套接字,或者其它表现的像流的类):
async_read(stream, buffer [, completion],handler):这种方法异步地从一个流读取。结束时,处理方法被调用。处理方法的格式是:void handler(const boost::system::error_ code & err, size_tbytes);。你能够选择指定一个完毕处理方法。完毕处理方法会在每一个read操作调用成功之后调用,然后告诉Boost.Asio async_read操作是否完毕(假设没有完毕,它会继续读取)。它的格式是:size_t completion(const
boost::system::error_code& err, size_tbytes_transfered) 。当这个完毕处理方法返回0时,我们觉得read操作完毕;假设它返回一个非0值,它表示了下一个async_read_some操作须要从流中读取的字节数。
接下来会有一个样例来具体展示这些。
async_write(stream, buffer [, completion],handler):这种方法异步地向一个流写入数据。參数的意义和async_read是一样的。
read(stream, buffer [, completion]):这种方法同步地从一个流中读取数据。參数的意义和async_read是一样的。
rite(stream, buffer [, completion]): 这种方法同步地向一个流写入数据。參数的意义和async_read是一样的。
° async_read(stream,stream_buffer [, completion], handler)
° async_write(strean,stream_buffer [, completion], handler)
° write(stream, stream_buffer[, completion])
° read(stream, stream_buffer[, completion])
首先,要注意第一个參数变成了流,而不单是socket。这个包括了socket但不不过socket。比方,你能够用一个Windows的文件句柄来替代socket。
当以下情况出现时,全部read和write操作都会结束:
可用的缓冲区满了(当读取时)或者全部的缓冲区已经被写入(当写入时)。
完毕处理方法返回0(假设你提供了这么一个方法)
发生错误时
以下的代码会异步地从一个socket中间读取数据直到读取到’\n’:
io_service service;
ip::tcp::socket sock(service);
char buff[512];
size_t up_to_en
int offset = 0;
stem::error_code &, size_t bytes) {
ter(const boost::s
y
for( size_t i = 0; i < bytes; ++i)
if ( buff[i + offset] == '\n')
return 0;
return 1;
}
void on_read(const boost::system::error_code &, size_t) {}
...
c_read(sock, buffer(buff), up_to_enter,on_read);
asy
n
Boost.Asio也提供了一些简单的完毕处理仿函数:
• transfer_at_least(n)
• transfer_exactly(n)
• transfer_all(
)
样例例如以下:
char buff[512];
void on_read(constboost::system::error_code &, size_t) {}
// 读取32个字节
async_read(sock, buffer(buff),transfer_exactly(32), on_read);
上述的4个方法,不使用普通的缓冲区,而使用由Boost.Asio的std::streambuf类继承来的stream_buffer方法,stl流和流缓冲区很复杂;以下是样例:
io_service service;
void on_read(streambuf& buf, constboost::system::error_code &,
size_t) {
std::istream in(&buf);
std::string line;
std::getline(in, line);
std::cout << "first line: "<< line << std::endl;
}
int main(int argc, char* argv[]) {
HANDLE file =::CreateFile("readme.txt", GENERIC_READ, 0, 0,
OPEN_ALWAYS, FILE_ATTRIBUTE_NORMAL | FILE_FLAG_OVERLAPPED,
0);
windows::stream_handle h(service, file);
streambuf buf;
uf, transfer_exactly(256),
async_read(h,
b
boost::bind(on_read,boost::ref(buf),_1,_2));
service.run();
}
在这里,我向你们展示了在一个Windows文件句柄上调用async_read。我们读取了前面的256个字符,然后把它们保存到缓冲区,当操作结束时。on_read被调用,然后创建std::istream来传递缓冲区,读取第一行(std::getline),最后把它输出到命令行中。
read_until/async_read_until方法
这些方法在条件满足之前一直读取:
async_read_until(stream, stream_buffer,delim, handler):这种方法启动一个异步read操作。read操作会在读取到某个分隔符时结束。分隔符能够是字符,std::string或者boost::regex。处理方法的格式为:void handler(const boost::system::error_code & err, size_tbytes);。
async_read_until(strem, stream_buffer,completion, handler):这种方法和之前的方法是一样的,可是没有分隔符,而是一个完毕处理方法。完毕处理方法的格式为:pair<iterator,bool> completion(iterator begin, iterator end);,当中迭代器的类型为buffers_iterator<streambuf::const_buffers_type>。你须要记住的是迭代器的类型是随机訪问的迭代器。你扫描整个区间(begin,end),然后认为read操作是否应该结束。你会返回一个结果对,第一个成员是一个指向最后被这种方法訪问的字符的迭代器;第二个成员当read操作须要结束时返回true,否则返回false。
read_until(stream, stream_buffer, delim):这种方法运行一个同步的read操作,參数的意义和async_read_until一样。
read_until(stream, stream_buffer,completion):这种方法运行一个同步的read操作,參数的意义和async_read_until一样。
以下这个样例会一直读取直到读到一个指定的标点符号
typedefbuffers_iterator<streambuf::const_buffers_type> iterator;
std::pair<iterator, bool>match_punct(iterator begin, iterator end) {
while ( begin != end)
if ( std::ispunct(*begin))
return std::make_pair(begin,true);
return std::make_pair(end,false);
}
void on_read(constboost::system::error_code &, size_t) {}
...
streambuf buf;
async_read_until(sock, buf, match_punct,on_read);
假设我们想读到一个空格结束,我们须要把最后一行改动为:
async_read_until(sock, buff, ' ', on_read);
Boost.Asio c++ 网络编程翻译(10)的更多相关文章
- Boost.Asio c++ 网络编程翻译(20)
异步服务端 这个图表是相当复杂的:从Boost.Asio出来你能够看到4个箭头指向on_accept.on_read,on_write和on_check_ping. 着也就意味着你永远不知道哪个异步调 ...
- Boost.Asio c++ 网络编程翻译(11)
*_at方法 这些方法在一个流上面做随机存取操作.你来指定read和write操作从什么地方開始(offset): async_read_at(stream, offset, buffer [, co ...
- Boost.Asio c++ 网络编程翻译(14)
保持活动 假如,你须要做以下的操作: io_service service; ip::tcp::socket sock(service); char buff[512]; ... read(sock, ...
- Boost.Asio c++ 网络编程翻译(26)
Boost.Asio-其他特性 这章我们讲了解一些Boost.Asio不那么为人所知的特性.标准的stream和streambuf对象有时候会更难用一些,但正如你所见.它们也有它们的益处.最后,你会看 ...
- Boost.Asio c++ 网络编程翻译(21)
同步VS异步 Boost.Asio的作者做了一个非常惊艳的工作:它能够让你在同步和异步中自由选择,从而更好的适应你的应用. 在之前的章节中,我们学习了每种类型应用的框架,比方同步client,同步服务 ...
- Boost.Asio c++ 网络编程翻译(16)
TCP异步服务端 核心功能和同步服务端的功能类似,例如以下: class talk_to_client : public boost::enable_shared_from_this<talk_ ...
- Boost.Asio c++ 网络编程翻译(18)
同步服务端 同步服务端也相当简单.它须要两个线程,一个负责接收新的client.另外一个负责处理已经存在的client. 它不能使用单线程:等带一个新的client是一个堵塞操作,所以我们须要另外一个 ...
- boost.asio系列——socket编程
asio的主要用途还是用于socket编程,本文就以一个tcp的daytimer服务为例简单的演示一下如何实现同步和异步的tcp socket编程. 客户端 客户端的代码如下: #include &l ...
- 使用boost.asio实现网络通讯
#include <boost/asio.hpp> #define USING_SSL //是否加密 #ifdef USING_SSL #include <boost/asio/ss ...
随机推荐
- Android仿Win8界面的button点击
今天没事的时候,感觉Win8的扁平化的button还是挺好看的,就研究了下怎样在安卓界面实现Win8的扁平化button点击效果. 发现了一个自己定义的View能够实现扁平化button效果,话不多说 ...
- SSH密码错误几次后封禁登录IP
#!/bin/bash yum -y install vixie-cron crontabs mkdir -p /usr/local/cron/ cat > /usr/local/cron/ss ...
- ContentValues的使用
什么是 ContentValues类? ContentValues类和 Hashtable比较类似,它也是负责存储一些名值对,但是它存储的名值对当中的名是一个String类型,而值都是基本类型. 插入 ...
- php课程 13-43 mysql的数据结构是什么
php课程 13-43 mysql的数据结构是什么 一.总结 一句话总结:cs结构,客户端,服务器 1.常用的比较出名的数据库有哪些? SQL数据库(关系型):1.收费:DB2SqlserverOra ...
- String类型转Long类型需要注意的问题
转自:https://blog.csdn.net/m819177045/article/details/52669785/
- JavaScript 实现表格单列按字母排序
<!DOCTYPE HTML> <html> <head> <meta charset="utf-8"> <title> ...
- BZOJ3262: 陌上花开(三维偏序,CDQ分治)
Description 有n朵花,每朵花有三个属性:花形(s).颜色(c).气味(m),用三个整数表示. 现在要对每朵花评级,一朵花的级别是它拥有的美丽能超过的花的数量. 定义一朵花A比另一朵花B要美 ...
- 1.字符设备驱动------Linux中断处理体系结构
一.中断处理体系结构的初始化 Linux内核将所有的中断统一编号,使用一个irq_desc结构数组来描述这些中断;每个数组项对应一个中断,也可能是一组中断,它们共用相同的中断号,里面记录了中断的名称. ...
- 微信浏览器的html5页面显示配置等问题汇集 1,禁止微信浏览器分享页面链接 (定点更新)
公司新需求,要求从安卓IOS应用分享到微信的链接页面不允许二次转发,所以开始编程第一步,上网找资料... 网上大神就是多,不消两分钟,找到方案,很简单,上代码先: wx.config({ debug: ...
- eclipse4.3怎么集成jadclipse追踪源代码,现在windows-preferences-java
A.将net.sf.jadclipse_3.2.4.jar复制到D:\leaf\eclipse\plugins目录下. B.在d:\leaf下建立ecliplsePlungin\jadclips ...