Node 简介和环境搭建

发布于 2021-01-19 12:56:11 字数 4554 浏览 1151 评论 0

本来开始写博客的时候只是想写一下关于 MongoDB 的使用总结的,后来觉得还不如干脆写一个 node 项目实战教程实战。写教程一方面在自己写的过程中需要考虑更多的东西,另一方面希望能对 node 入门者有一些帮助。

相信大多数跟随前面一章教程来到这一章的读者大多分成两类:

  • 第一类是知道 node,想学习 node,但是英文匮乏或者网上教程不给力,希望有一个全面一点的教程入门的;
  • 第二类应该是 node 入门,但是之前使用的不是类似MongoDB这种非关系型数据库,想学习一下的。

从我个人的角度看来,我希望自己前一段时间关于前端和后端的协同开发经验能够得到提炼和分享。

Nodejs 简介

Node.js是一个基于Chrome JavaScript运行时建立的一个平台,用来方便地搭建快速的 易于扩展的网络应用。Node.js借助事件驱动, 非阻塞I/O模型变得轻量和高效,非常适合 运行在分布式设备的数据密集型的实时应用。

对于不熟悉 JavaScript 的读者来说,上面的概念可能并不是很亲切,但其实 node 作为一个平台,他的很多特性基本上就是 JavaScript 本身的特性。本文假设你对JavaScript有一定的了解,对于上面的概念给出本人自己的解释。

我想首先介绍一下宿主环境这个概念。一门语言在运行的时候,需要一个环境,叫做宿主环境。对于JavaScript,宿主环境最常见的是web浏览器,浏览器提供了一个JavaScript运行的环境,这个环境里面,需要提供一些接口,好让JavaScript引擎能够和宿主环境对接。

JavaScript引擎才是真正执行JavaScript代码的地方,常见的引擎有V8(目前最快JavaScript引擎、Google生产)、JavaScript core。JavaScript引擎主要做了下面几件事情:(1)一套与宿主环境相联系的规则;(2)JavaScript引擎内核(基本语法规范、逻辑、命令和算法);(3)一组内置对象和API;(4)其他约定。

但是环境不是唯一的,也就是JavaScript不仅仅能够在浏览器里面跑,也能在其他提供了宿主环境的程序里面跑,最常见的就是nodejs。同样作为一个宿主环境,nodejs也有自己的JavaScript引擎 V8。根据官方的定义 Node.js is a platform built on Chrome’s JavaScript runtime for easily building fast, scalable network applications

因此我们可以这么理解 node,它不是一门语言,而是一个平台。node 是JavaScript运行的一个宿主环境,它提供了一些接口,能够让JavaScript引擎与这个宿主环境对接。真正执行JavaScript代码的是JavaScript引擎,也就是V8引擎,这个引擎值Google生产的,是当前最快的JavaScript引擎,没有之一。

Nodejs 特性解析

到现在为止我们就知道了 Nodejs 的真面貌,但是还不清楚它的几个特点。Nodejs 的这些特点,也可以说是 JavaScript 的特点,毕竟 Nodejs 只是一个平台,而执行的代码,都是 JavaScript 代码。所以我斗胆尝试解释 JavaScript/Nodejs 的这几个特点,如有错误,非常欢迎指出。

同步与异步

JavaScript 里面的调用分成两种,一种是同步调用,一种是异步调用。简单的区别就是,调用的时候能够立马得到结果的就是同步调用,不能立马得到结果的就是异步调用。同步非常好理解,一个简单的数学运算就是同步调用。

异步的话,可以举一个常见的例子,一篇文章可能有很多很多评论,在页面加载好的时候,只显示前面几条,如果用户想查看更多,就会点击加载更过评论按钮。为了提高用户体验,通常是发送Ajax请求,获取更多内容。这个请求并不能立马得到回应,而是等待数据返回。等数据返回之后,再动态加载到页面中,这就是异步调用。

单线程与Event Loop

为了要弄清楚事件驱动与非阻塞I/O,我们需要大概了解JavaScript运行的时候的原理。也就需要知道单线程和Event Loop这两个概念。什么是单线程呢?我们知道线程是CPU调度的基本单位,单线程意味着JavaScript线程在某一个时刻只能执行一个调用。

刚刚又说了,调用分成同步调用和异步调用,这两者的区别决定了在执行JavaScript代码的时候,总是先执行完所有同步代码,再去查看是否有异步调用需要执行。这个原理其实就是JavaScript事件驱动的底层原理 Event Loop

再具体阐述什么是 Event Loop 之前,我先借用一张好图:

我们可以看到,在JavaScript执行栈中,总是先把所有的调用推入栈中,如果遇到了异步调用,就会放到WebAPIs中,然后继续执行后面的代码,等到WebAPIs中的异步调用执行完成后,不是立马执行,而是先放到callback queue里面,那么这个队列里面的函数怎么执行?什么时候执行?

中介者就是Event Loop了,他会一直询问callback queue里面有无需要执行的代码,如果有,推送到执行栈的最后面,等待执行。如果执行栈中没有同步代码在执行,就会立即执行这个这个回调。拿我们平常写JavaScript常见的绑定事件处理程序来讲,属于DOM事件,如果产生了DOM事件,比如点击鼠标,那么这个时候就会放到callback queue里,Event Loop的下一次询问,就会放到执行栈里面。

通常执行栈里面的同步代码是很少的,所以通常这个点击后的事件立马就执行了。 以上就是Event Loop的大致解析。

非阻塞 I/O 与事件驱动

如果你理解了刚刚的Event Loop,应该就明白了什么叫非阻塞I/O和事件驱动了。首先还是讲讲什么是非阻塞I/O

线程在执行中如果遇到磁盘读写或网络通信(统称为I/O操作),通常要耗费较长的时间,这时操作系统会剥夺这个线程的CPU控制权,使其暂停执行,同时将 资源让给其他的工作线程,这种线程调度方式称为阻塞。当I/O操作完毕,操作系统将这个线程的阻塞状态解除,恢复其对CPU的控制权,令其继续执行。这种I/O模式就是通常的同步式I/O(Synchronous I/O).

当线程遇到I/O操作时,不会以阻塞的方式等待I/O操作的完成或数据的返回,而只是将I/O请求发送到操作系统,继续执行下一条语句。当操作系统完成I /O操作时,以事件的形式通知执行I/O操作的线程,线程会在特定时候处理这个事件。为了处理异步I/O,线程必须有事件循环,不断地检查有没有未处理的事件,依次处理。

如果JavaScript是阻塞I/O,拿之前加载更多评论的例子看来,只要数据还没有从服务器返回,所有后续的操作都将阻塞,比如点击其他绑定了事件处理程序的按钮。幸运的事,正如《Nodejs开发指南》提到的一样,线程必须有事件循环,也就是刚刚说到的Event Loop!那么非阻塞I/O也就自然而然地理解了。

至于事件驱动,它和非阻塞I/O应当是因果关系的,因为JavaScript是基于事件驱动的,所以成就了非阻塞I/O的特性。因为要做到异步的话,常用的就是发送异步请求,请求相应之后,执行回调事件,事件在JavaScript中无处不在。

Node 安装

与 Python 等安装不同的是,Nodejs 在 Windows 下面的安装反而比在 Linux下面简单的多。你可以通过node -v命令来检测是否安装成功:

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。
列表为空,暂无数据

关于作者

JSmiles

生命进入颠沛而奔忙的本质状态,并将以不断告别和相遇的陈旧方式继续下去。

0 文章
0 评论
84961 人气
更多

推荐作者

醉城メ夜风

文章 0 评论 0

远昼

文章 0 评论 0

平生欢

文章 0 评论 0

微凉

文章 0 评论 0

Honwey

文章 0 评论 0

qq_ikhFfg

文章 0 评论 0

    我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
    原文