boost-Asio 基础学习2 --socket 服务端和客户端简单通讯

已经写了两期文章了!这是第三期 现在也到使用asio库实现一些基础的小功能了🤓服务端和客户端简单的发送消息

0.了解

服务端所需要的方法或类

①asio::ip::address::from_string(string "0.0.0.0") 方法 主要用于把字符串地址转换为地址 返回address类型
asio::ip::tcp::endpoint endpoint( address , port_type num) 参数1是地址 参数2是端口号
 asio::ip::tcp::acceptor tcp_acceptor( asio::io_context , asio::ip::tcp::endpoint ); 接收器 参数1异步对象 参数二是地址和端口号组合后的 endpoint 类型  服务端需要使用到它的构造函数 
asio::ip::tcp::socket tcp_socket(asio::io_context ) 绑定异步对象
⑤acceptor.accept(&socket )方法 等待接收连接 会阻塞直到连接成功 参数1监听socket
asio::buffer("内容或者是字符串类型来接收") asio用于接收和发送时的数据类型
socke.write_some(asio::buffer) 像目标服务器发送的内容
tcp_socket.read_some(asio::buffer(&)) 这个buffer用于来接收客户端像我们发送数据
⑨socke.remote_endpoint()方法 获取客户端的地址和端口

客户端所需要的方法或类

服务端有标注的我就不赘述了

①asio::ip::tcp::resolver resolver(io_context); 创建个解析对象
②asio::ip::tcp::resolver::query query("地址","端口"); 查找 参数1可以是域名主机 参数二端口
③asio::ip::tcp::resolver::iterator iterator; 迭代器它可以迭代该域名主机的所有地址 

这三个功能在上篇文章细讲过icon-default.png?t=N7T8https://blog.youkuaiyun.com/weixin_48158333/article/details/139568329?spm=1001.2014.3001.5501
④asio::connect(socket,iterator);参数1绑定socket 参数二绑定迭代器 它如果阻塞几秒会直接报错导致程序崩溃 最好配合try语句使用 

结束~ 以上有些功能 类似endpoint from_string address在地址拼接里面讲过icon-default.png?t=N7T8https://blog.youkuaiyun.com/weixin_48158333/article/details/139551107

1.服务端

服务端代码实操

1先创建个几乎任何操作都需要它的  io_context 或 io_service 两者二选一即可
asio::io_context io_context;//
是 Boost.Asio 中处理异步操作的核心组件。它管理异步操作的调度和执行,
提供事件循环,并支持多线程处理
2快速的创建 要监听绑定的地址和端口
asio::ip::address address = asio::ip::address::from_string("192.168.5.95");
asio::ip::tcp::endpoint endpoint(address, 8821);
3给接受器绑定我们的地址
asio::ip::tcp::acceptor acceptor(io_context, endpoint);
4创建socket对象
asio::ip::tcp::socket tcp_socket(io_context);
5监听

        传递的是引用! 等价于tcp_socket = acceptor.accept();

        它会阻塞主线程

acceptor.accept(tcp_socket); //它会阻塞等待链接
6创建对话内容并且发送到客户端

        有两种写法asio::write(tcp_socket,asio::buffer("hello client 你好 客户端")) ; 等价于 👇

	 char getcontent[1024] = "123 hello client";
	tcp_socket.write_some(asio::buffer(getcontent));

为什么创建个字符串?是因为方便我们接下来接收客户端的信息

7获取客户端发送的信息和长度
size_t contentlength = tcp_socket.read_some(asio::buffer(getcontent));
std::cout << "答应: " << std::string(getcontent, contentlength)<<std::endl;
8最后获取对方的地址信息
std::cout<<"地址: " << tcp_socket.remote_endpoint() << std::endl;

服务端全部代码

void ASIOsocket()
{
	//server
	asio::io_context io_context;
	asio::ip::address address = asio::ip::address::from_string("192.168.5.95");
	asio::ip::tcp::endpoint endpoint(address, 8821);

	asio::ip::tcp::acceptor acceptor(io_context, endpoint);

	asio::ip::tcp::socket tcp_socket(io_context);

	//传递的是引用! 等价于
	tcp_socket = acceptor.accept();
	//acceptor.accept(tcp_socket); //它会阻塞等待链接

	char getcontent[1024] = "123 hello client";
	//asio::write(tcp_socket,asio::buffer("hello client 你好 客户端")) ; 等价于 👇
	tcp_socket.write_some(asio::buffer(getcontent));

	size_t contentlength = tcp_socket.read_some(asio::buffer(getcontent));

	std::cout << "地址: " << tcp_socket.remote_endpoint() << std::endl;

	std::cout << "答应: " << std::string(getcontent, contentlength) << std::endl;

}

客户端

步骤

1.创建异步对象 asio::io_context io_context;
asio::io_context io_context;
2.创建socket对象
asio::ip::tcp::socket tcp_socket(io_context);
3.创建解析器对象
asio::ip::tcp::resolver resolver(io_context);
4.创建查找对象 并且填入端口 和主机域名或地址
	asio::ip::tcp::resolver::query query("192.168.5.95","8821");
5.创建个迭代器并解析
asio::ip::tcp::resolver::iterator iterator = resolver.resolve(query);
6.创建try包裹住接下来的代码

因为asio::connect();连接超时会报错 所以需要使用try围住它避免程序崩溃 之后的代码全部在try{内部书写}

	try
	{
		//会超时报错
// 确保iterator是个迭代器而不是tcp::endpoint
//asio::connect(tcp_socket,asio::ip::tcp::endpoint(asio::ip::address::from_string("192.168.5.95"), 8821));
//踩坑的错误
		asio::connect(tcp_socket, iterator);

	}
	catch (const std::exception&)
	{
		std::cout << "content: 等待超时" << std::endl;
	}
7之后就可以像服务端一样创建个字符类型的数组设定好大小 先接收服务端的信息
char read[1024];

size_t length = tcp_socket.read_some(asio::buffer(read));
std::cout << "content:" << std::string(read, length);
8.向服务端发送收到了
	tcp_socket.write_some(asio::buffer("OK~~~"));

客户端全部代码:

void AsioBaseClient()
{
	asio::io_context io_context;
	asio::ip::tcp::socket tcp_socket(io_context);
	
	asio::ip::tcp::resolver resolver(io_context);
	
	asio::ip::tcp::resolver::query query("192.168.5.95","8821");

	asio::ip::tcp::resolver::iterator iterator = resolver.resolve(query);

	//asio::connect(tcp_socket, iterator);
	//稍微等待之后会报错 最好添加try 避免程序错误
	try
	{
		//会超时报错
// 确保iterator是个迭代器而不是tcp::endpoint
//asio::connect(tcp_socket,asio::ip::tcp::endpoint(asio::ip::address::from_string("192.168.5.95"), 8821));
//踩坑的错误

		asio::connect(tcp_socket, iterator);
		char read[1024];

		size_t length = tcp_socket.read_some(asio::buffer(read));
		std::cout << "content:" << std::string(read, length);
		tcp_socket.write_some(asio::buffer("OK~~~"));
	}
	catch (const std::exception&)
	{
		std::cout << "content: 等待超时" << std::endl;
	}




	return;
}

RUN

服务端👇

客户端👇


END

全部代码-今天对应的是AsioBaseClient() 和  ASIOsocket();

我也是现学现卖!也是最近需要 这些只是我简单的理解🤝 有错误或不正确的地方欢迎评论指正🤝

bilibili/抖音/快手/csdn/知乎/或各大平台同名: w傲奇w

公众号:奇怪世界StrangeWorld 编写日期:2024年6月13日

拜拜~

个人博客(未建设好)

        

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值