前言

本综述文章旨在帮助读者深入理解下Node.js的本质,不去关注应用的细节,我认为真正的技术问题只有在动手写代码的时候才会遇到,那个阶段解决问题才是真正有意义的。
 

发展史

Node.js是Ryan Dahl 2009年对外发布的开源醒目,后来该项目被Joyent公司注意到并于2010年成为Joyent公司的一个子项目。2016年微软与Joyent公司合作,Node.js在windows上得到支持。
目前Node.js的版本为V6.11,周围已经形成了一个庞大的生态系统。
 

特性分析

Node.js is a JavaScript runtime built on Chrome's V8 JavaScript engine. Node.js uses an event-driven, non-blocking I/O model that makes it lightweight and efficient. Node.js' package ecosystem, npm, is the largest ecosystem of open source libraries in the world.
上面是Node.js的官方描述,其中包含了Node.js最突出的特点。
1、Javascript runtime
这个描述解答了Node.js是什么的问题。它是一个Javascript 运行环境,类似于JVM之于Java,Node.js负责将Javascript转化为计算机可以识别的机器语言,同时对外提供API。传统上javascript依附于浏览器运行:
Node.js舍弃了浏览器,直接与js引擎对接,通过js引擎提供的API,Node.js可以完成其他后端语言(java)所能完成的一切功能,例如文件操作、网络通信、设备管理等等。
下面说下Node.js所采用的js引擎——V8,这是目前世界上最快的js引擎,来自于Google Chrome项目,用C++语言编写,凭借Goole强大的技术支持,它的执行速度已经接近本地代码的执行速度。
除了V8以外,Node.js的还是用了libev和libio库支持事件驱动和异步IO,如图所示,libuv是在libev和libeio的基础上抽象出的一层,对于POSIX系统,libuv利用epoll或者kqueue,而在Windows系统中,libuv使用了IOCP机制,以在不同的平台下实现统一的高性能。
2、non-blocking IO and event-driven
先说说非阻塞IO,假设一个请求要读取数据库,db.query(select * from table),这个过程涉及磁盘读取与网络通信,耗时很长,下面是几种服务器处理方式。
(1)如果是单线程+阻塞处理,线程会等待数据读取完毕才继续处理,同时后续的请求也得等待,这样的系统是不能忍受的。
 
(2)好在现在的后端容器都是支持多线程+阻塞的,其解决思路如下:
等待数据的线程继续等待,如果有新请求就重新创建一个线程,把cpu让给新的线程,待原线程得到数据后再把cpu切换给原线程。这样做有什么缺点么?
一是大量请求的情况下线程数目不断增加,浪费大量系统资源。
二是CPU在处理上下文切换的时候也浪费了不少时间。
 
(3)Node.js的解决思路则完全不一样。它被设计成单线程+非阻塞的。
所有的请求都在一个线程处理,一旦遇到耗时的请求,cpu不等待数据返回,而是接着处理后续的请求。那么问题来了,前面请求的数据到达后,如何返回给前端呢?这就要牵扯到Node.js的另外一个特性——事件驱动。
在上面的简化模型中,所有的请求会依次进入线程的处理循环中,每个请求自带回调函数,当耗时请求接受完数据后,回调函数自动被调用,重新进去循环处理,直到数据被返回给前端。
这样能让单个CPU充分运行起来,没有丝毫等待,同时避免了在不同的线程中频繁切换引起的浪费。根据统计,Node.js相对传统的PHP+Nginx,在性能上有明显提升。
这种设计思路就是为微服务web系统而生的,因为web服务的特点就是请求密集、计算量小、要求快速响应。
 

Node.js的缺点

1、对于长期占据CPU的请求,后续的请求不能得到及时处理,产生较大延时,所以Node.js不适合计算密集型应用。
2、Node.js专注单线程处理,在多核环境中,必须总多进城才能充分利用多核,因此增加了设计难度。
3、Node.js的异步式编程模式不太符合一般的程序控制思路,给编码和调试带来不少困难。

常用辅助框架

1、npm(Node Package Manager)

Node.js本身提供的API比较底层,完全依靠Node.js实现一个系统对技术人员要求比较高。不过现在已经有大量的第三方支持供开发者使用。为了更好地使用和管理这些第三方提供的包,Node.js官方提供了一个基于命令行的包管理工具——npm.

npm完全由javascript实现,不属于Node.js的一部分。不过在Node.js0.6开始,npm会自动包含在发行版中。

2、Express

参考
《Node.js开发指南》
《为什么我要用 Node.js》http://blog.jobbole.com/53736/

Node.js综述的更多相关文章

  1. 快速使用node.js进行web开发

    首先关于node.js的学习,这里推荐一本比较好的教程,nodejs web开发指南,该书通俗易懂地将node.js语言特性讲解完之后,又从一个项目角度带领读者使用node.js学习web开发.相信这 ...

  2. node.js 初学 自我笔记整理 day01

     node.js   概念问题: Node.js 是一个基于 Chrome V8 引擎的 JavaScript 运行环境.   npm是一个node的包管理工具  ,也是一个网站  ,还是一条命令.N ...

  3. 【转】Node.js到底是用来做什么的

    Node.js的到底是用来做什么的 在阐述之前我想放一个链接,这是国外的一个大神,对于node.js非常好的一篇介绍的文章,英文比较好的朋友可以直接去阅读,本文也很大程度上参考了这篇文章,也同时感谢知 ...

  4. node.js学习(三)简单的node程序&&模块简单使用&&commonJS规范&&深入理解模块原理

    一.一个简单的node程序 1.新建一个txt文件 2.修改后缀 修改之后会弹出这个,点击"是" 3.运行test.js 源文件 使用node.js运行之后的. 如果该路径下没有该 ...

  5. 利用Node.js的Net模块实现一个命令行多人聊天室

    1.net模块基本API 要使用Node.js的net模块实现一个命令行聊天室,就必须先了解NET模块的API使用.NET模块API分为两大类:Server和Socket类.工厂方法. Server类 ...

  6. Node.js:进程、子进程与cluster多核处理模块

    1.process对象 process对象就是处理与进程相关信息的全局对象,不需要require引用,且是EventEmitter的实例. 获取进程信息 process对象提供了很多的API来获取当前 ...

  7. Node.js:理解stream

    Stream在node.js中是一个抽象的接口,基于EventEmitter,也是一种Buffer的高级封装,用来处理流数据.流模块便是提供各种API让我们可以很简单的使用Stream. 流分为四种类 ...

  8. Node.js:Buffer浅谈

    Javascript在客户端对于unicode编码的数据操作支持非常友好,但是对二进制数据的处理就不尽人意.Node.js为了能够处理二进制数据或非unicode编码的数据,便设计了Buffer类,该 ...

  9. node.js学习(二)--Node.js控制台(REPL)&&Node.js的基础和语法

    1.1.2 Node.js控制台(REPL) Node.js也有自己的虚拟的运行环境:REPL. 我们可以使用它来执行任何的Node.js或者javascript代码.还可以引入模块和使用文件系统. ...

随机推荐

  1. pytest文档8-html报告报错截图+失败重跑

    前言 做web自动化的小伙伴应该都希望在html报告中展示失败后的截图,提升报告的档次,pytest-html也可以生成带截图的报告. conftest.py 1.失败截图可以写到conftest.p ...

  2. [Android Pro] android 杀死进程的方法

    1: 杀死自己进程的方法 android.os.Process.killProcess(Process.myPid()); 2:杀死别人进程的方法(不能杀死自己) -------a: activity ...

  3. [Android Pro] Android应用性能测试之CPU和内存占用(转载)

    首先稍做分析一下测试环境:我们知道CPU和内存占用是一个实时变化的状态,而市面上还没有具体的哪款android应用能做到实时监控CPU和内存占用并使用log日志保存.考虑到android的底层框架是基 ...

  4. GLSL 在OpenGL中向shader传递信息【转】

    http://blog.csdn.net/hgl868/article/details/7872219 引言 一个OpenGL程序可以用多种方式和shader通信.注意这种通信是单向的,因为shade ...

  5. Tensorflow之调试(Debug) && tf.py_func()

    Tensorflow之调试(Debug)及打印变量 tensorflow调试tfdbg 几种常用方法: 1.通过Session.run()获取变量的值 2.利用Tensorboard查看一些可视化统计 ...

  6. hadoop压缩框架

    一般来说,计算机处理的数据都存在一些冗余度,同时数据中间,尤其是相邻数据间存在着相关性,所以可以通过一些有别于原始编码的特殊编码方式来保存数据,使数据占用的存储空间比较小,这个过程一般叫压缩.和压缩对 ...

  7. Sqlserver DateTime转换成SMALLDATETIME时“产生一个超出范围的值”

    工作中遇到一个问题,A表中字段(DateTime1)的数据类型为DateTime,新建了一张表B的SMALLDATETIME1字段的数据来自A表的DateTime1 但在将A表字段DateTime1导 ...

  8. Redis数据类型--List

    Redis列表是简单的字符串列表,依照插入顺序排序. 你能够加入一个元素到列表的头部(左边)或者尾部(右边) LPUSH 命令插入一个新的元素到头部, RPUSH插入一个新元素到尾部. 当一个这两个操 ...

  9. 图结构练习——BFS——从起始点到目标点的最短步数(邻接表+BFS)

    图练习-BFS-从起点到目标点的最短步数 Time Limit: 1000ms   Memory limit: 65536K  有疑问?点这里^_^ 题目描写叙述 在古老的魔兽传说中.有两个军团,一个 ...

  10. POJ 2823 UESTCoj 1221 Sliding Window 单调队列 经典入门题

    题意:给出一个序列,求出每连续k个数字中最大的数和最小的数. 这是道单调队列裸题,直接写就行了. 本来用deque写出来后,发现在poj上硬是超时了,在discuss上看很多人也在抱怨超时的问题,据说 ...