Boost. Asio c ++ network programming translation (26), boost. asio Network Programming
Boost. Asio-Other Features This chapter describes some features that Boost. Asio is not so well known. Standard stream and streambuf objects are sometimes more difficult to use, but as you can see, they also have their benefits. Finally, you will see the late Boost. Asio coroutine, which makes your asynchronous code very readable. This is an amazing feature.
Before reading this section, you need to understand STL stream and STL streambuf objects. Boost. Asio supports two types of buffer when processing I/O operations:
- Boost: asio: buffer (): This buffer is associated with a Boost. Asio operation (the buffer we use is passed to a Boost. Asio Operation)
- Boost: asio: streambuf: This buffer inherits from std: streambuf. It can be used together with STL stream in network programming.
Throughout the book, the most common examples are as follows:
size_t read_complete(boost::system::error_code, size_t bytes){ ... } char buff[1024]; read(sock, buffer(buff), read_complete); write(sock, buffer("echo\n"));
Generally, this can meet your needs. If you want to be more complex, you can use streambuf to implement it. This is the simplest and worst thing you can do with a streambuf object:
Streambuf buf;
read(sock, buf);
This will always read that the streambuf object is full, and then because the streambuf object can re-open the space to obtain more space, it will basically read that the connection is closed. You can use read_until to read a specific string all the time:
Streambuf buf;
Read_until (sock, buf, "\ n ");
This example will always read "\ n", add it to the end of the buffer, and then exit the read method. Write something to a streambuf object. You need to do something similar to the following:
streambuf buf; std::ostream out(&buf); out << "echo" << std::endl; write(sock, buf);
This is very intuitive; you pass your streambuf object in the constructor to build an STL stream and write it into the message you want to send, then, use write to send the buffer content.
Boost. Asio and STL streamBoost. Asio have done a great job in integrating STL stream and network. That is to say, if you are already using STL extensions, you will certainly have a large number of classes that reload operators <and>. Reading or writing from the socket is as easy as walking in the park. Suppose you have the following code snippet:
struct person { std::string first_name, last_name; int age;
}; std::ostream& operator<<(std::ostream & out, const person & p) {
return out << p.first_name << " " << p.last_name << " " << p.age; }
std::istream& operator>>(std::istream & in, person & p) {
return in >> p.first_name >> p.last_name >> p.age;
}
Sending this person over the network is as simple as the following code snippet:
Streambuf buf; std: ostream out (& buf); person p ;//... Initialize p out <p <std: endl; write (sock, buf );
The other part can be easily read:
read_until(sock, buf, "\n"); std::istream in(&buf); person p; in >> p;
Use a streambuf object. Of course, it also includes the std: ostream used for writing and the best part of the std: istream used for reading. The final encoding is natural:
- When writing something to be sent through the network, it is very likely that you will have multiple fragments of data. Therefore, you need to add the data to a buffer. If the data is not a string, you need to convert it into a string first. When the <operator is used, all these operations are performed by default.
- Similarly, in another part, when reading a message, you need to parse it. That is to say, when reading data from a segment, if the data is not a string, you need to convert it to a string. When you use the> operator to read something, this is also done by default.
Finally, I want to give a very famous and cool tip. Use the following code snippet to output streambuf content to the console.
Streambuf buf;... std: cout <& buf <std: endl; // output all content to the console.
Similarly, use the following code snippet to convert its content to a string:
std::string to_string(streambuf &buf) { std::ostringstream out; out << &buf; return out.str();
}