图解NodeJS【基于事件、回调的单线程高性能服务器】原理
2015-10-23 23:44
302 查看
刚开始了解Node感觉很吊,各种说高性能,可是一直不理解为什么单线程会比多线程快?为什么异步IO比非阻塞IO快?因此,本篇在阅读相关书籍后,根据自己的理解,整理此文,如有错误,仅代表理论不精,必当修改,以免误导他人。还请多多指正.....
关于阻塞IO和非阻塞IO
系统内核只有两种IO模式—— 阻塞IO和非阻塞IO。这里的IO可不仅仅是读取文件内容,而是更为广泛的概念。比如Socket啊,网络Socket,磁盘读取等等,这些相比于CPU计算都是很耗时的。下图为阻塞IO的工作模式:
阻塞IO在需要获取数据进行IO操作时,CPU会等待,当读取完成后,再继续运行。那么很容易就能想到,如果读取很耗时,CPU就会长期处于阻塞状态,显然效率很低。
再看看非阻塞IO:
非阻塞IO在进行IO操作时,会直接返回。然后CPU该干嘛干嘛,只不过需要一定的策略来确定什么时间请求数据完成,这个时候就需要一些轮训策略了,比如select poll等等。那么这个也应该能想到,当有长期的IO操作,会白白执行大量的查询操作,效率也不高。(当然目前的系统内的非阻塞IO都是很高级的玩法,卤煮也没有仔细研究,就不献丑了)
异步IO与Node工作原理
通过上面两种典型的IO操作,很显然,一种理想的模型是,有IO操作时,系统去执行IO操作,CPU该干嘛干嘛,当请求数据完成后,就通知CPU继续执行刚才没有完成的工作。Node就是利用了javascript的回调函数思想,实现这种工作模式。
那么为什么单线程的Node会效率很高呢?什么又是事件机制呢?
原来,一直说的单线程,都是javascript端的,Node底层还是使用c来实现,因此底层仍然是多线程的。只不过,Node基于不同的操作系统linux或者windows之上实现了一个封装层,用户执行的操作命令会转交给这个封装层,由它再去判断操作系统,进而调用相应平台的c代码。
有点跑题了,简单的说,就是Node只是表面暴露给用户的javascript代码是单线程的,底层还是多线程的。
说到事件机制,就要上图了!简单的解释一下,当我们使用Node的时候,会在javascript触发一些命令调用方法,这些方法会被包装成一个对象,放入线程池,然后前面的方法就返回了,继续执行下面的JS代码。
线程池中采用多线程的方式执行,执行完的对象放入事件循环队列。
事件循环队列采用类似while(true)这种循环的方式,不断的查看是否有事件,并且读取是否包含回调,由于前面回调函数被包装到对象中,这里直接调用执行就可以了。
通过这三种阶段,就实现了 【 异步请求——>回调 】 的工作模式。相关文章推荐
- 极路由H3C(华3)版本号正确的填写格式
- NodeAsp——像开发NodeJS应用一样玩转ASP
- Algorithms—222.Count Complete Tree Nodes
- NodeJS 实现基于 token 的认证应用
- [leetcode]Remove Nth Node From End of List
- Populating Next Right Pointers in Each Node
- Node.js 究竟是什么?
- 关于mysql的emoji表情问题(服务器node)
- nodeJs修改上传文件的大小限制
- Node.js笔记(一)项目的建立
- Node.js笔记(一)项目的建立
- mysql node emoji问题
- nodejs+phantomjs+casperjs
- nodejs实战express笔记之增加编辑与删除功能
- nodejs中exports与module.exports的区别
- [Leetcode] Remove Nth Node From End of List
- windows下sublime text的node.js开发环境搭建
- node.js学习二(Express4.x)
- node.js学习一(node入门)
- Remove Nth Node From End of List