浙江体彩20选5: 燕赵风采20选5走势图

北京 切换校区

全国24小时免费热线

400-009-1906

Http Server : 一个差生的逆袭

时间:2019-01-09   来源:尚学堂   阅读:231

  我刚毕业那会儿,国家还是包分配工作的,我的死党小明被分配到了一个叫数据库的大城市,天天都可以坐在高端大气上档次的机房里,在那里专门执行SQL查询优化,工作稳定又舒适;

  隔壁宿舍的小白被送到了编译器镇,在那里专门把C源文件编译成EXE程序,虽然累,但是技术含量非常高,工资高,假期多。

  我成绩不太好,典型的差生,四级补考了两次才过,被发配到了一个不知道什么名字的村庄,据说要处理什么HTTP请求,这个村庄其实就是一个破旧的电脑,令我欣慰的是可以上网,时不时能和死党们通个信什么的。

  不过辅导员说了,我们都有光明的前途。

 

  1、HttpServer1.0

  HTTP是个新鲜的事物,能够激起我一点点工作的兴趣,不至于沉沦下去。

  一上班,操作系统老大扔给我一大堆文档:“这是HTTP协议,两天看完!”

  我这样的英文水平,这几十页的英文HTTP协议我不吃不喝不睡两天也看不完,死猪不怕开水烫,慢慢磨吧。

  两个星期以后,我终于大概明白了这HTTP是怎么回事:无非是有些电脑上的浏览器向我这个破电脑发送一个预先定义好的文本(Httprequest),然后我这边处理一下(通常是从硬盘上取一个后缀名是html的文件),然后再把这个文件通过文本方式发回去(httpresponse),就这么简单。

  唯一麻烦的实现,我得请操作系统给我建立Http层下面的TCP连接通道,因为所有的文本数据都得通过这些TCP通道接收和发送,这个通道是用socket建立的。

  弄明白了原理,我很快就搞出了第一版程序,这个程序长这个样子:

 ?。ㄗⅲ合昵椴渭游恼隆墩糯笈值膕ocket》)

  看看,这些socket,bind,listen,accept...都是操作系统老大提供的接口,我能做的也就是把他们组装起来:先在80端口监听,然后进入无限循环,如果有连接请求来了,就接受(accept),创建新的socket,最后才可以通过这个socket来接收,发送http数据。

  老大给我的程序起了个名称,HttpServer,版本1.0。

  这个名字听起来挺高端的,我喜欢。

  我兴冲冲的拿来实验,程序启动了,在80端口“蹲守”,过了一会儿就有连接请求了,赶紧Accept,建立新的socket,成功!接下来就需要从socket中读取HttpRequest了。

  可是这个receive调用好慢,我足足等了100毫秒还没有响应!我被阻塞(block)住了!

  操作系统老大说:“别急啊,我也在等着从网卡那里读数据,读完以后就会复制给你?!?/span>

  我乐的清闲,可以休息一下。

  可是操作系统老大说:“别介啊,后边还有很多浏览器要发起连接,你不能在这儿歇着啊?!?/span>

  我说不歇着怎么办?receive调用在你这里阻塞着,我除了加入阻塞队列,让出CPU让别人用还能干什么?

  老大说:“唉,大学里没听说过多进程吗?你现在很明显是单进程,一旦阻塞就完蛋了,想办法用下多进程,每个进程处理一个请求!”

  老大教训的是,我忘了多进程并发编程了。

 

  2、Http2.0:多进程

  多进程的思路非常简单,当accept连接以后,对于这个新的socket,不在主进程里处理,而是新创建子进程来接管。这样主进程就不会阻塞在receive上,可以继续接受新的连接了。

  我改写了代码,把Httpserver升级为V2.0,这次运行顺畅了很多,能并发的处理很多连接了。

  这个时候Web刚刚兴起,我这个HttpServer访问的人还不多,每分钟也就那么几十个连接发过来,我轻松应对。

  由于是新鲜事物,我还有资本给搞数据库的小明和做编译的小白吹吹牛,告诉他们我可是网络高手。

  没过几年,Web迅速发展,我所在的破旧机器也不行了,换成了一个性能强悍的服务器,也搬到了四季如春的机房里。

  现在每秒中都有上百个连接请求了,有些连接持续的时间还相当的长,所以我经常得创建成百上千的进程来处理他们,每个进程都得耗费大量的系统资源,很明显操作系统老大已经不堪重负了。

  他说:“咱们不能这么干了,这么多进程,光是做进程切换就把我累死了?!?/span>

  “要不对每个Socket连接我不用进程了,使用线程?”

  “可能好一点,但我还是得切换线程啊,你想想办法限制一下数量吧?!?/span>

  我怎么限制?我只能说同一时刻,我只能支持x个连接,其他的连接只能排队等待了。

  这肯定不是一个好的办法。

 

  3、HttpServer3.0:Select模型

  老大说:“我们仔细合计合计,对我来说,一个Socket连接就是一个所谓的文件描述符(FileDescriptor,简称fd,是个整数),这个fd背后是一个简单的数据结构,但是我们用了一个非常重量级的东西--进程--来表示对它的读写操作,有点浪费啊?!?/span>

  我说:“要不咱们还切换回单进程模型?但是又会回到老路上去,一个receive的阻塞就什么事都干不了了”

  “单进程也不是不可以,但是我们要改变一下工作方式?!?/span>

  “改成什么?”我想不透老大在卖什么关子。

  “你想想你阻塞的本质原因,还不是因为人家浏览器还没有把数据发过来,我自然也没法给你,而你又迫不及待的想去读,我只好把你阻塞。在单进程情况下,一阻塞,别的事儿都干不了?!?/span>

  “对,就是这样”

  “所以你接受了客户端连接以后,不能那么着急的去读,咱们这么办,你的每个socketfd都有编号,你把这些编号告诉我,就可以阻塞休息了”

  我问道:“这不和以前一样吗?原来是调用receive时阻塞,现在还是阻塞”

  “听我说完,我会在后台检查这些编号的socket,如果发现这些socket可以读写,我会把对应的socket做个标记,把你唤醒去处理这些socket的数据,你处理完了,再把你的那些socketfd告诉我,再次进入阻塞,如此循环往复?!?/span>

  我有点明白了:“这是我们俩的一种通信方式,我告诉你我要等待什么东西,然后阻塞,如果事件发生了,你就把我唤醒,让我做事情?!?/span>

  “对,关键点是你等我的通知,我把你从阻塞状态唤醒后,你一定要去遍历一遍所有的socketfd,看看谁有标记,有标记的做相应处理。我把这种方式叫做select”

  我用select的方式改写了Httpserver,抛弃了一个socket请求对于一个进程的模式,现在我用一个进程就可以处理所有的socket了。

 

  4、HttpServer4.0:epoll

  这种称为select的方式运行了一段时间,效果还不错,我只管把socketfd告诉老大,然后等着他通知我就行了。

  有一次我无意中问老大:“我每次最多可以告诉你多少个socketfd?”

  “1024个”

  “那就是说我一个进程最多只能监控1024个socket了?”

  "是的,你可以考虑多用几个进程啊"

  这倒是一个办法,不过"select"的方式用的多了,我就发现了弊端,最大的问题就是我从阻塞中恢复以后,需要遍历这1000多个socketfd,看看有没有标志位需要处理。

  实际的情况是,很多socket并不活跃,在一段时间内浏览器并没有数据发过来,这1000多个socket可能只有那么几十个需要真正的处理,但是我不得不查看所有的socketfd,这挺烦人的。

  难道老大不能把那些发生了变化的socket告诉我吗?

  我把这个想法给老大说了下,他说:“嗯,现在访问量越来越大,select方式已经不满足要求,我们需要与时俱进了,我想了一个新的方式,叫做epoll”

  “看到没有,使用epoll和select其实类似“老大接着说:”不同的地方是第3步和第4步,我只会告诉你那些可以读写的socket,你呢只需要处理这些'ready'的socket就可以了“

  “看来老大想的很周全,这种方式对我来说就简单的多了?!?/span>

  我用epoll把HttpServer再次升级,由于不需要遍历全部集合,只需要处理哪些有变化的,活跃的socket文件描述符,系统的处理能力有了飞跃的提升。

  我的HttpServer受到了广泛的欢迎,全世界有无数人在使用,最后死党数据库小明也知道了,他问我:“大家都说你能轻松的支持好几万的并发连接,真是这样吗?”

  我谦虚的说:“过奖,其实还得做系统的优化啦?!?/span>

  他说:“厉害啊,你小子走了狗屎运了啊?!?/span>

  我回答:“毕业那会儿辅导员不是说过吗,每个人都有光明的前途?!?/span>

 ?。ㄍ辏?/span>

相关资讯

  • 北京校区
  • 山西校区
  • 郑州校区
  • 武汉校区
  • 四川校区
  • 长沙校区
  • 深圳校区
  • 上海校区
  • 广州校区
  • 保定招生办

北京海淀区校区(总部):北京市海淀区西三旗街道建材城西路中腾建华商务大厦东侧二层尚学堂
北京京南校区:北京亦庄经济开发区科创十四街6号院1号楼 赛蒂国际工业园
咨询电话:400-009-1906 / 010-56233821
面授课程: JavaEE培训、 大数据就业班培训、 大数据云计算周末班培训、 零基础大数据连读班培训、 大数据云计算高手班培训、 人工智能周末班培训、人工智能+Python全栈培训、 H5+PHP全栈工程师培训

山西学区地址:山西省晋中市榆次区大学城大学生活广场万科商业A1座702

郑州学区地址:河南电子商务产业园6号楼4层407
咨询电话:0371-55177956

武汉学区地址:湖北省武汉市江夏区江夏大道26号 宏信悦谷创业园4楼
咨询电话:027-87989193

四川学区地址:成都市高新区锦晖西一街99号布鲁明顿大厦2栋1003室
咨询电话:028-65176856 / 13880900114

网址://www.cssxt.com/
咨询电话:0731-83072091

深圳校区地址:深圳市宝安区航城街道航城大道航城创新创业园A4栋210(固戍地铁站C出口)
咨询电话:0755-23061965 / 18898413781

上海尚学堂松江校区地址:上海市松江区荣乐东路2369弄45号绿地伯顿大厦2层
咨询电话:021-67690939

广州校区地址:广州市天河区元岗横路31号慧通产业广场B区B1栋6楼尚学堂(地铁3号线或6号线到“天河客运站”D出口,右拐直走约800米)
咨询电话:020-2989 6995

保定招生办公室

地址:河北省保定市竞秀区朝阳南大街777号鸿悦国际1101室

电话:15132423123

Copyright 2006-2019 北京尚学堂科技有限公司  京ICP备13018289号-19  京公网安备11010802015183  
媒体联系:18610174079 闫老师  

Java基础班,免费试学三周

700| 546| 391| 445| 483| 314| 83| 619| 247| 776|