Muduo
Muduo是陈硕大佬开发的,一个基于非阻塞IO和事件驱动的C++高并发网络编程库
这是一个基于主从Reactor模型的网络编程库,线程模型是one loop per thread
意思是一个线程只能有一个事件循环(event loop), 用于响应计时器和事件
一个文件描述符只能由一个线程进行读写,也就是一个Tcp连接,必须归属于一个EventLoop管理
基本逻辑是这样的
所谓的主从Reactor就是,在主线程中有一个主Reactor进行事件触发,而在其他其他线程中就是普通的Reactor进行事件触发
在主线程中主要任务就是监控新连接的到来,保证尽可能高效的获取新建连接,再按照负载均衡的方式分发到普通Reactor的线程中,对对应的IO事件进行监控
主从Reactor必然是一个多执行流的并发模式,也就是one thread one loop
Server常见接口
TcpServer类
这个类用来生成服务器对象
构造函数是这样的
TcpServer(EventLoop *loop,
const InetAddress &listenAddr,
const string &nameArg,
Option option = kNoReusePort);
第一个参数loop对象在下面来介绍
第二个参数是一个地址信息,结构是这样的
class InetAddress : public muduo::copyable
{
public:
InetAddress(StringArg ip, uint16_t port, bool ipv6 = false);
};
包含了ip和端口两个信息,是服务器需要监听和绑定的地址
第三个参数是字符串的名称
最后一个参数是一个选项,是否启用端口重用的功能
enum Option
{
kNoReusePort,
kReusePort,
};
我们直到当请求释放连接时,会有一段time wait状态,这段时间内同一个端口号是无法再次被绑定使用的
打开端口重用就可以解除这个限制,继续使用这个端口号
setThreadNum()
void setThreadNum(int numThreads);
这个成员函数就是用于设置从属Reactor线程的数量的
Start()
void start();
启动事件监听
setConnectionCallback()
这是一个回调函数,需要我们自己来编写
typedef std::function<void(const TcpConnectionPtr &)> ConnectionCallback;
void setConnectionCallback(const ConnectionCallback &cb)
{
connectionCallback_ = cb;
}
当连接建立成功时,会调用这个回调接口,完成我们的功能
setMessageCallback()
这也是一个回调函数,是用于业务处理的回调函数
typedef std::function<void(const TcpConnectionPtr &,
Buffer *,
Timestamp)>
MessageCallback;
void setMessageCallback(const MessageCallback &cb)
{
messageCallback_ = cb;
}
当收到连接的新的消息的时候,调用的函数
EventLoop类
这个类主要是用于事件监控和业务处理,在构造TcpServer之前,就需要构造这个EventLoop对象,最重要的就是loop成员函数
TcpConnection类
connected()和disconnect()是用于查看连接状态的
send()是用于发送数据的
服务器搭建
#include "muduo/include/muduo/net/TcpServer.h"
#include "muduo/include/muduo/net/EventLoop.h"
#include "muduo/include/muduo/net/TcpConnection.h"
#include "../logs/Xulog.h"
#include "TransLate.hpp"
#include <iostream>
#include <functional>
#include <unordered_map>
class TranslateServer
{
public:
TranslateServer(int port) : _server(&_baseloop,
muduo::net::InetAddress("0.0.0.0", port),
"TranslateServer",
muduo::net::TcpServer::kReusePort)
{
// 参数绑定
auto func_1 = std::bind(&TranslateServer::onConnection, this, std::placeholders::_1);
auto func_2 = std::bind(&TranslateServer::onMessage, this, std::placeholders::_1,
std::placeholders::_2, std::placeholders::_3);
// 设置回调函数
_server.setConnectionCallback(func_1);
_server.setMessageCallback(func_2);
}
// 启动服务器
void start()
{
_server.start(); // 开始事件监听
_baseloop.