服务端
server.h
#pragma once #include <iostream> #include <boost/asio.hpp> #include <boost/system/error_code.hpp> #include <boost/asio/ip/address.hpp> #include <boost/shared_ptr.hpp> #include <boost/bind.hpp> using namespace boost::asio; class server { public: virtual ~server(); typedef server this_type; typedef ip::tcp::acceptor acceptor_type; typedef ip::tcp::endpoint endpoint_type; typedef ip::tcp::socket socket_type; typedef std::shared_ptr<socket_type> sock_ptr; private: io_service m_io; acceptor_type m_acceptor; public: server() : m_acceptor(m_io, endpoint_type(ip::tcp::v4(), 6688)) { accept1(); } void run() { m_io.run(); } void accept() { sock_ptr sock(new socket_type(m_io)); m_acceptor.async_accept(*sock, bind(&this_type::accept_handler, this, boost::asio::placeholders::error, sock)); } //通过lambda表达式来实现bind void accept1(); void accept_handler(const boost::system::error_code& ec, sock_ptr sock); void write_handler(const boost::system::error_code& ec) { std::cout << "send msg complete." << std::endl; } //未调用 void write_handler2(const boost::system::error_code& ec, std::size_t n) { std::cout << "send msg " << n << std::endl; } };
server.cpp
#include "pch.h" #include "server.h" server::~server() { } void server::accept_handler(const boost::system::error_code& ec, sock_ptr sock) { if (ec) { return; } std::cout << "client:"; std::cout << sock->remote_endpoint().address() << std::endl; sock->async_write_some(buffer("hello, client. it's from server send you."), bind(&this_type::write_handler, this, boost::asio::placeholders::error)); accept(); } void server::accept1() { sock_ptr sock(new socket_type(m_io)); m_acceptor.async_accept(*sock, [this, sock](const boost::system::error_code& ec) { if (ec) { return; } sock->async_send(buffer("hello client, this msg generate function using lambda expression."), [](const boost::system::error_code&, std::size_t) { std::cout << "send msg complete." << std::endl; } ); accept1(); } ); }
调用
// TcpSynServer.cpp : 此文件包含 "main" 函数。程序执行将在此处开始并结束。 // #include "pch.h" #include <iostream> #include "server.h" int main() { try { std::cout << "server start." << std::endl; server svr; svr.run(); } catch (const std::exception& ec) { std::cout << ec.what() << std::endl; } getchar(); std::cout << "Hello World!\n"; } // 运行程序: Ctrl + F5 或调试 >“开始执行(不调试)”菜单 // 调试程序: F5 或调试 >“开始调试”菜单 // 入门提示: // 1. 使用解决方案资源管理器窗口添加/管理文件 // 2. 使用团队资源管理器窗口连接到源代码管理 // 3. 使用输出窗口查看生成输出和其他消息 // 4. 使用错误列表窗口查看错误 // 5. 转到“项目”>“添加新项”以创建新的代码文件,或转到“项目”>“添加现有项”以将现有代码文件添加到项目 // 6. 将来,若要再次打开此项目,请转到“文件”>“打开”>“项目”并选择 .sln 文件
客户端
client.h
#pragma once #include <iostream> #include <memory> #include <boost/asio.hpp> #include <boost/system/error_code.hpp> #include <boost/asio/ip/address.hpp> #include <boost/bind.hpp> using namespace boost::asio; class client { public: virtual ~client(); typedef client this_type; typedef ip::tcp::endpoint endpoint_type; typedef ip::address address_type; typedef ip::tcp::socket socket_type; typedef std::shared_ptr<socket_type> sock_ptr; typedef std::vector<char> buffer_type; private: io_service m_io; buffer_type m_buf; endpoint_type m_ep; public: client() : m_buf(100, 0), m_ep(address_type::from_string("127.0.0.1"), 6688) { start1(); } void run() { m_io.run(); } void start() { sock_ptr sock(new socket_type(m_io)); sock->async_connect(m_ep, bind(&this_type::conn_handler, this, boost::asio::placeholders::error, sock)); } //使用lambda表达式实现bind void start1(); void conn_handler(const boost::system::error_code& ec, sock_ptr sock); void read_handler(const boost::system::error_code& ec, sock_ptr sock) { if (ec) { return; } std::cout << &m_buf[0] << std::endl; sock->async_read_some(buffer(m_buf), bind(&client::read_handler, this, boost::asio::placeholders::error, sock)); } };
client.cpp
#include "pch.h" #include "client.h" client::~client() { } void client::conn_handler(const boost::system::error_code& ec, sock_ptr sock) { if(ec) { return; } std::cout << "receive from server :" << sock->remote_endpoint().address() << std::endl; sock->async_read_some(buffer(m_buf), bind(&client::read_handler, this, boost::asio::placeholders::error, sock)); } void client::start1() { sock_ptr sock(new socket_type(m_io)); sock->async_connect(m_ep, [this, sock](const boost::system::error_code& ec) { if (ec) { return; } sock->async_read_some(buffer(m_buf), [this, sock](const boost::system::error_code& ec, std::size_t) { read_handler(ec, sock); } ); } ); }
调用
// TcpSynClient.cpp : 此文件包含 "main" 函数。程序执行将在此处开始并结束。 // #include "pch.h" #include <iostream> #include "client.h" int main() { try { std::cout << "client start." << std::endl; client cl; cl.run(); } catch (const std::exception& ec) { std::cout << ec.what() << std::endl; } getchar(); std::cout << "Hello World!\n"; } // 运行程序: Ctrl + F5 或调试 >“开始执行(不调试)”菜单 // 调试程序: F5 或调试 >“开始调试”菜单 // 入门提示: // 1. 使用解决方案资源管理器窗口添加/管理文件 // 2. 使用团队资源管理器窗口连接到源代码管理 // 3. 使用输出窗口查看生成输出和其他消息 // 4. 使用错误列表窗口查看错误 // 5. 转到“项目”>“添加新项”以创建新的代码文件,或转到“项目”>“添加现有项”以将现有代码文件添加到项目 // 6. 将来,若要再次打开此项目,请转到“文件”>“打开”>“项目”并选择 .sln 文件
note:
- bind.hpp不能忘记添加
- bind实现函数到handler的适配
- lambda表达式的使用