NodeJ中的单线程和非阻塞I / O操作有什么区别?

时间:2013-06-04 22:21:02

标签: node.js

我一直在阅读并尽可能多地浏览NodeJs代码,但我对此有点困惑:

Node是单线程的意思是什么?非阻塞I / O是什么意思?我可以通过生成子进程来实现第一个,通过使用异步库来实现第二个进程。但是我想清楚它的含义以及非阻塞I / O如何仍然会减慢你的应用程序。

1 个答案:

答案 0 :(得分:9)

我会尽力解释。

单线程意味着Node.js Javascript运行时 - 在特定时间点 - 仅从它加载的所有代码中执行一段代码。实际上,它从某个地方开始,并在所有指令(调用堆栈)中向下工作,直到完成为止。当它正在执行代码时,没有任何东西可以中断此过程,并且所有I / O都必须等待。值得庆幸的是,大多数调用堆栈都相对较短,我们在Node.js中做的很多事情都比“簿记”更多,而不是CPU重。

然而,作为单线程,任何需要很长时间的指令对于系统中的响应性来说都是一个巨大的问题。运行时一次只能做一件事,所以一切都必须等到该指令完成。如果任何“I / O”指令(例如从磁盘读取)将阻止执行,那么系统将在那时不必要地不可用。

但幸运的是,我们有非阻塞I / O.

而不是等待读取文件:

console.log(readFileSync(filePath))

您编写代码以便不要等待读取文件:

readFile(filePath)

readFile调用几乎立即返回(可能在几纳秒内),因此运行时可以继续执行下一步的指令。但是如果readFile调用在读取数据之前返回,则readFile调用无法返回文件内容。这就是回调的来源:

readFile(filePath, function(err, contents) { console.log(contents))

然而,readFile通话几乎立即返回。运行时可以继续。它将完成当前的工作(readFile之后的所有指令)。除了存储对它的引用之外,传递的函数没有任何功能。

然后,在稍后的某个时间点(可能是10毫秒,100毫秒或1000毫秒),当读取文件完成时,将使用文件的完整内容作为第二个参数调用回调。在此之前,运行时可以完成任意数量的其他批量工作。

现在,我将讨论有关生成子进程和异步库的注释。你们两个帐户都错了。

  • 产生子进程是一种让Node.js使用CPU核心的方法。作为单线程,单个Node.js没有使用多个核心的目的。但是,如果您使用的是多核计算机,则可能需要使用所有这些核心。因此,启动多个Node.js.过程

  • Async库不会为您提供非阻塞I / O,Node.js会为您提供。 Node.js没有给你自己的东西,是处理来自多个回调的数据的简单方法。 Async库可以帮助解决这个问题。

由于我不是Node.js内部的专家,我欢迎更正!

相关问题: