tortoise从服务器获取项目_重复利用,一劳永逸,一套用于网络通信的服务器架构...

作为一个程序员,相信对于设计开发的五大原则,都是耳熟能详,但是在实际项目中,不是每一个开发者都能够正确的应用。

本文将介绍用于网络通信的服务器架构,被成功应用于实际的项目中,并且取得不错的效果,它基于依赖倒置原则,真正实现了功能的复用。

本文将简单介绍依赖倒置原则,然后总体说明用于网络通信的服务器架构,最后再结合实际代码详细说明该套服务器架构的核心。

一、依赖倒置

为了介绍什么是依赖倒置原则,这里通过一个例子进行说明。假设现在有一个按钮,可以控制灯的打开或者关闭。

一般的实现方式如下图所示,但是这样的实现方式就导致按钮只能控制灯。如果想要让按钮复用控制其他的设备,在不修改Button类的情况下,那是没办法做到的。

40d38c4a167764a04bf136e740a1f4a2.png

那么如何解决上面的问题呢,通过添加接口SwitchDevice来解决。然后灯Lamp实现接口SwitchDevice。这就解除了Button对Lamp的依赖,当Button要控制其他设备的时候,只需要其他设备实现接口SwitchDevice即可,不需要改动Button。

fd5a8550b94ea3ca9fff8691bd7bf214.png

上面介绍的例子,就是遵循了依赖倒置原则。它有两个基本的要点,分别为:

A、高层模块不应该依赖于低层模块,二者都应该依赖于抽象

B、抽象不应该依赖于细节,细节应该依赖于抽象。

并且常常是客户拥有服务接口。

二、服务器架构

网络通信的客户服务器模式,服务器端通常都是监听接收客户端的连接请求,并且处理客户端发送的数据,处理完成之后,进行回复。

下图是本文要重点介绍的服务器架构的类图。JMsgTranceiver是消息的传送者,负责监听并接收客户端发送的数据,JNetBreakHander是负责处理网络中断,JMsgOutbox是发件箱,负责将邮箱中的信息发送给客户端,JMsgInbox是收件箱,负责处理客户端的数据,并且将其发送给JMsgDispatcher, JMsgDispatcher则是将其收到的消息分发给其他模块进行处理。

从下面的类图中,可以看出服务器架构遵循了依赖倒置的原则,定义了网络中断接口JNetBreakHanderInterface和消息分发的接口JMsgDispatcherInterface, 使得服务器通信模块与其他模块之间分离,实现了服务器通信模块的独立和复用性。

774e62c17ac8c944a3b1125b41c87d06.png

三、实现功能

本章节为了简洁,达到理清服务器架构的目的,没有将全部代码贴出来,只是展示重要的代码段。

定义接口

客户服务端的通信,需要定义通信的结构体。

90b6c3a0cdb69622319311e894985027.png

网络中断的接口实现如下,主要定义了两个纯虚函数,分别为OnConnect和OnDisconnect。OnConnect是处理网络连接事件,OnDisconnect是处理网络断开事件。

1267c20b60f8bf1d8045f6d6ee592bbd.png

消息分发的接口实现如下,定义了纯虚函数HandleMsg,用于将消息分发给其他模块处理。

9073bb479f90c98d29fd5ea48be678c0.png

消息传送者

消息传送者采用单例模式,头文件定义如下

78ed02185676a98b78e202780bf050d3.png

JMsgTransceiver的首次使用,需要调用Init函数,其内部实现如下,接收了网络中断处理者和消息分发处理器,然后创建了收件箱、发件箱,并且启动线程处理函数。

8363d2e61b88e5426a3468e950e87a4f.png

线程处理函数中,创建服务端socket, 并且等待客户端的连接,一旦接收到客户端的连接,则首先处理网络连接事件,然后循环处理网络消息,如果网络中断,那么调用接口OnDisconnect,处理网络断开事件。

84aad084dc580c1b0d16a1860d5a1ca8.png

循环处理网络消息,主要是处理可读和可写两个事件。

9050e5dbb6d87a3021240e7ad92f09d9.png

如果有数据可读,那么调用接口RecvData,首先从收件箱JMsgInbox获取分配的内存用于接收客户端的数据,如果有接收到数据,那么执行收件箱提供的函数Advance处理数据。

f2a7949adb39bc16d79cad115301eac8.png

如果有数据可写,那么调用接口SendData, 从发件箱JMsgOutbox获取数据来发送,如果发送数据成功,那么执行发件箱提供的函数Advance处理数据。

fe3b71b31283fb6b6566717f46dce80a.png

发件箱

发件箱的功能是将其他模块的数据存储到列表std::list中,然后提供接口供外部使用。

第一个函数GetOutStream是获取待发送的消息流

5f334740ec406c12def502d263c936ee.png

第二个函数Advance是移动消息流指针,因为每次发送的数据不一定按照预期的设置发送成功,所以需要判断发送的数据是否完成,如果完成,那么释放消息内存。

0d00b172d486958e2957d8e08bba81ad.png

收件箱

收件箱的功能是将消息分发给其他模块进行处理。

函数GetInStream是获取待接收的消息流, 主要区分是在接收消息头还是消息体。

54991a1d671f5259fa6bf663f86053f5.png

函数Advance同样是移动消息流指针,但是与发件箱不同的是,当接收到完整的数据之后,将调用分发接口,分发数据到其他模块处理。

ff331ff1d974bffb76070f8467ba6f96.png

消息分发

消息分发类继承了接口JMsgDispacherInterface,实现了纯虚函数HandleMsg。具体如何实现,依据具体项目场景。这里是当HandleMsg接收到数据,那么通过条件变量的方式通知线程从列表中获取数据进行处理。本项目是创建了5个固定的线程,主要是为了提高分发的效率。

9783d35a28f00025d65b0ed15d4c6af7.png

四、使用功能

那么如何使用服务器架构,其实很简单,只需要程序启动的时候,执行下面的代码,那么服务器端就可以等待客户端的连接,并且处理数据。

8bd3e21aaf9bedf9fe296372d466928f.png

五、总结

本文首先介绍了依赖倒置的原则,然后再介绍用于网络通信的服务器架构,该架构遵循了依赖倒置的原则,实现了模块的复用。

Python网络爬虫与推荐算法新闻推荐平台:网络爬虫:通过Python实现新浪新闻的爬取,可爬取新闻页面上的标题、文本、图片、视频链接(保留排版) 推荐算法:权重衰减+标签推荐+区域推荐+热点推荐.zip项目工程资源经过严格测试可直接运行成功且功能正常的情况才上传,可轻松复刻,拿到资料包后可轻松复现出一样的项目,本人系统开发经验充足(全领域),有任何使用问题欢迎随时与我联系,我会及时为您解惑,提供帮助。 【资源内容】:包含完整源码+工程文件+说明(如有)等。答辩评审平均分达到96分,放心下载使用!可轻松复现,设计报告也可借鉴此项目,该资源内项目代码都经过测试运行成功,功能ok的情况下才上传的。 【提供帮助】:有任何使用问题欢迎随时与我联系,我会及时解答解惑,提供帮助 【附带帮助】:若还需要相关开发工具、学习资料等,我会提供帮助,提供资料,鼓励学习进步 【项目价值】:可用在相关项目设计中,皆可应用在项目、毕业设计、课程设计、期末/期中/大作业、工程实训、大创等学科竞赛比赛、初期项目立项、学习/练手等方面,可借鉴此优质项目实现复刻,设计报告也可借鉴此项目,也可基于此项目来扩展开发出更多功能 下载后请首先打开README文件(如有),项目工程可直接复现复刻,如果基础还行,也可在此程序基础上进行修改,以实现其它功能。供开源学习/技术交流/学习参考,勿用于商业用途。质量优质,放心下载使用。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值