背景:
•因为工作中要用到文件上传功能,在网上搜了下库。搜到了Poco,里面的库有http自带功能。由于:加密、应用程序服务框架、数据库操作类(SQLite,MongoDB)等对工作中很有用,所以继BOOST,Google的protobuf后又引入了。 •刚开始服务端用BOOST的asio做的,性能很不错,只是担心以后维护麻烦,既然引入了Poco,自然就把服务端网络程序改成了Poco实现了,这一实现不要紧,一实现发现问题了,发现Poco是基于SELECT模型的,性能很差。无奈之下,本着吸取ASIO和Poco的优势,又将BOOST的ASIO重新用Poco的设计思想实现了一遍(由于有了两者深刻的认识,2个多小时就搞定)。 •于是担心,如果HTTP采用Poco也会有同样的问题,于是在网上搜到了AVHttp的库,看上去很牛B的样子,还加了里面的群。
群:
里面确实有几个高手,比如菜博士、jack,他们视MFC,Poco,ACE,Java如垃圾(我看了Poco,接口和java的非常像)。极力推崇BOOST,STL。
昨天在群里发表了个话题,我说了下服务器实现的思路(核心框架)。自以为还不错,没想到引来了不同意见。jack还卖了个关子,直到晚上10点左右才出来解释原因。
进入正题–服务器核心框架
我的思路是这样的:
开一个线程专门接收socket消息,接收到消息后,用智能指针封装下,分发出去,然后开线程处理,处理完后,再回调,发送出去。菜博士说我受到ACE的影响,我说绝对没有,没接触过ACE。(注:ACE是网上公认的设计模式的典范,他对设计模式很不感冒)。然后又说这样的实现有这样那样的缺点。现在想起来,可能是受了Poco的enqueueNotification的影响。如下图:
思路很像,只是是全异步的(没有waitXXXX,是立即处理的)
我的做法是关于socket部分用一个io(boost::asio::io_service),单独线程;接收到消息封装后就不管了,直接发送给处理的io(多个),固定线程数,比如5个。然后进行处理,处理完后,再通过智能指针包装下,再通过消息发送。
菜说这个做法有问题,后来jack也做了补充。他说了他们的想法,经过一个晚上的思考,我总于想明白了。确实效率很高。
我用比较通俗的语言概括:
1.我的做法像是工厂流水线,一个消息,比如有多个肥皂进来,分给多个工人,他们各自处理(比如包装),然后把处理结果(包装好的肥皂盒)再放回流水线上。具体为:多个io,每个io一个线程,分别进行处理。 2. 菜博士和java的做法是像切洋肉末 ,即将所有处理看成一个"处理",然后通过多个线程处理,处理完及完毕。好比你给他一块肉,他就像一个娴熟的厨师,叭叭叭切好,再给你肉末,完事!一个io,多个线程,分发处理。
对照我先前实现的框架,发现改动很少,呵呵。