给一个使用boost asio 同步方法的Chat客户端和服务端的做法
Synchronous Chat Client
#include <string>
#include <boost/asio.hpp>
using namespace std;
using boost::asio::ip::tcp;
int main()
{
boost::asio::io_service io;
tcp::resolver resolver(io);
tcp::resolver::query query(tcp::v4(), "127.0.0.1", "1234");
tcp::resolver::iterator iterator = resolver.resolve(query);
tcp::socket sock(io);
boost::asio::connect(sock, iterator);
for(;;)
{
string line;
HANDLE handle = GetStdHandle(STD_OUTPUT_HANDLE);
SetConsoleTextAttribute(handle, FOREGROUND_GREEN | FOREGROUND_INTENSITY); //input text: green
cout << "[Sent] ";
do
{
//cannot send empty message
getline(cin, line);
}
while(line.empty());
sock.write_some(boost::asio::buffer(line));
SetConsoleTextAttribute(handle, FOREGROUND_GREEN | FOREGROUND_RED | FOREGROUND_INTENSITY); //output text: yellow
char reply[1024];
memset(reply, 0, 1024);
sock.read_some(boost::asio::buffer(reply, 1024));
cout << "[Recieved] " << reply << endl << endl;
}
return 0;
}
Synchronous Chat Server
#include <iostream>
#include <boost/asio.hpp>
#include <boost/thread.hpp>
using namespace std;
using boost::asio::ip::tcp;
//使用信号量保证输出不会出现截断
boost::mutex mutex;
void session(tcp::socket* sock)
{
mutex.lock();
cout << "Client " << sock->remote_endpoint() << " Connecting..." << endl;
mutex.unlock();
char data[1024];
for(;;)
{
memset(data, 0, 1024);
boost::system::error_code error;
size_t lenght = sock->read_some(boost::asio::buffer(data), error);
mutex.lock();
cout << "Client " << sock->remote_endpoint() << " Said: " << data << endl;
mutex.unlock();
if (error == boost::asio::error::eof)
break; //connection closed cleanly by peer
else if (error)
{
mutex.lock();
cerr << "Read Error: " << error.message() << endl;
mutex.unlock();
break;
}
sock->write_some(boost::asio::buffer(data), error);
if(error)
{
mutex.lock();
cerr << "Write Error: " << error.message() << endl;
mutex.unlock();
break;
}
}
mutex.lock();
cout << "Client " << sock->remote_endpoint() << " Over" << endl << endl;
mutex.unlock();
delete sock;
}
int main()
{
boost::asio::io_service io;
tcp::endpoint ep(tcp::v4(), 1234);
tcp::acceptor acc(io, ep);
//同步方法一般是开个线程与client通信,主线程继续accept
for(;;)
{
tcp::socket* sock = new tcp::socket(io);
acc.accept(*sock);
boost::thread(&session,sock).detach();
}
return 0;
}