100

有没有办法创建线程来一次运行多个方法?

这样,如果任何方法在所有其他线程之间失败,都应该被杀死。

4

12 回答 12

100

新答案:虽然 node.js 过去不具备原生使用线程的能力,但后来添加了该能力。有关详细信息,请参阅https://nodejs.org/api/worker_threads.html

旧答案:每个 node.js 进程在设计上都是单线程的。因此,要获得多个线程,您必须拥有多个进程(正如其他一些海报所指出的那样,您还可以链接到一些库,这些库将使您能够在 Node 中使用线程,但如果没有这些库,则不存在这样的能力. 请参阅 Shawn Vincent 引用https://github.com/audreyt/node-webworker-threads的回答

您可以从主进程启动子进程,如 node.js 文档中所示: http ://nodejs.org/api/child_process.html 。此页面上的示例非常好,并且非常简单。

然后,您的父进程可以监视它启动的任何进程的关闭事件,然后可以强制关闭您启动的其他进程,以实现您正在谈论的一种失败所有停止策略的类型。

另请参阅: 多核机器上的 Node.js

于 2013-09-04T12:02:32.890 回答
34

还有至少一个库用于从 Node.js 中执行本机线程:node-webworker-threads

https://github.com/audreyt/node-webworker-threads

这基本上实现了node.js的Web Worker 浏览器 API 。

于 2014-03-23T16:54:59.540 回答
23

更新 2:

由于Node.js 12 LTS Worker 线程稳定的。


更新 1

从 Node v11.7.0开始,您不必使用--experimental-worker标志。

发行说明:https ://nodejs.org/en/blog/release/v11.7.0/


从 Node 10.5 现在开始支持多线程,但它是实验性的。希望这会很快稳定下来。

查看以下资源:

于 2018-07-02T05:13:50.400 回答
9

您可以使用 Napa.js 获得多线程。

https://github.com/Microsoft/napajs

“Napa.js 是一个基于 V8 构建的多线程 JavaScript 运行时,最初设计用于在 Bing 中开发具有不妥协性能的高度迭代服务。随着它的发展,我们发现它可以在 CPU 密集型任务中补充 Node.js ,具有在多个 V8 隔离中执行 JavaScript 并在它们之间进行通信的能力。Napa.js 作为 Node.js 模块公开,同时它也可以嵌入到没有 Node.js 依赖的主机进程中。

于 2017-10-19T19:26:44.993 回答
5

我需要在 Node.js 中实现真正的多线程,而对我有用的是线程包。它生成另一个进程,拥有自己的 Node.js 消息循环,因此它们不会相互阻塞。设置很简单,文档可以帮助您快速启动和运行。您的主程序和工作人员可以通过两种方式进行通信,如果需要,可以终止工作人员“线程”。

由于多线程和 Node.js 是一个复杂且广泛讨论的主题,因此很难找到适合特定需求的包。作为记录,这些对我不起作用

  • tiny-worker允许生成工人,但它们似乎共享相同的消息循环(但可能是我做错了什么 -线程有更多的文档让我相信它确实使用了多个进程,所以我一直这样做直到它工作)
  • webworker-threads不允许require在我需要的工作人员中使用模块

对于那些问我为什么需要真正的多线程的人:对于涉及 Raspberry Pi 和中断的应用程序。一个线程处理这些中断,另一个负责存储数据(以及更多)。

于 2017-12-04T10:24:59.453 回答
5

nodejs 10.5.0 版本宣布了 Node.js 中的多线程。该功能仍处于试验阶段。现在有一个新的worker_threads模块可用。

如果您运行Node.js v10.5.0 或更高版本,则可以开始使用工作线程,但这是一个实验性 API。默认情况下不可用:您需要  在调用 Node.js 时使用--experimental-worker启用它。

这是一个启用ES6worker_threads的示例,在 12.3.1 版本上测试

//package.json

  "scripts": {
  "start": "node  --experimental-modules --experimental- worker index.mjs"
  },

现在,您需要从worker_threads导入 Worker 。注意:为了支持 ES6 ,您需要声明带有“.mjs”扩展名的js文件。

//index.mjs
import { Worker } from 'worker_threads';

const spawnWorker = workerData => {
    return new Promise((resolve, reject) => {
        const worker = new Worker('./workerService.mjs', { workerData });
        worker.on('message', resolve);
        worker.on('error', reject);
        worker.on('exit', code => code !== 0 && reject(new Error(`Worker stopped with 
        exit code ${code}`)));
    })
}

const spawnWorkers = () => {
    for (let t = 1; t <= 5; t++)
        spawnWorker('Hello').then(data => console.log(data));
}

spawnWorkers();

最后,我们创建一个workerService.mjs

//workerService.mjs
import { workerData, parentPort, threadId } from 'worker_threads';

// You can do any cpu intensive tasks here, in a synchronous way
// without blocking the "main thread"
parentPort.postMessage(`${workerData} from worker ${threadId}`);

输出:

npm 运行开始

Hello from worker 4
Hello from worker 3
Hello from worker 1
Hello from worker 2
Hello from worker 5
于 2019-05-27T07:29:55.000 回答
4

如果您使用的是 Rx,在 rxjs-cluster 中插入插件以将工作拆分为并行执行是相当简单的。(免责声明:我是作者)

https://www.npmjs.com/package/rxjs-cluster

于 2016-02-14T17:41:02.450 回答
2

现在也有https://github.com/xk/node-threads-a-gogo,虽然我不确定项目状态。

于 2015-02-19T05:44:27.997 回答
2

NodeJS 现在包括线程(作为回答时的实验性功能)。

于 2019-03-08T23:08:02.260 回答
0

您可能正在寻找Promise.race(本机 I/O 竞赛解决方案,而不是线程)

假设您(或其他搜索此问题的人)想要竞争线程以避免失败并避免 I/O 操作的成本,这是一种简单且原生的方式来完成它(不使用线程)。Node 设计为单线程(查找事件循环),因此尽可能避免使用线程。如果我的假设是正确的,我建议您使用Promise.racewith setTimeout(链接中的示例)。使用此策略,您将竞争一个 Promise 列表,每个 Promise 都尝试一些 I/O 操作并在出现错误(否则超时)时拒绝该 Promise。该Promise.race声明在第一次解决/拒绝后继续,这似乎是您想要的。希望这对某人有帮助!

于 2017-01-15T05:33:08.073 回答
0

Node.js 不使用线程。根据其发明者的说法,这是一个关键特征。在它发明的时候,线程是缓慢的、有问题的和困难的。Node.js 是在对一种高效的单核替代方案进行调查后创建的。大多数 Node.js 爱好者仍然引用 ye olde 的论点,好像线程在过去 50 年中没有得到改进。

如您所知,Node.js 用于运行 JavaScript。JavaScript 语言也经过多年发展。它现在有使用多核的方法——即线程的作用。因此,通过 JavaScript 的进步,您可以在应用程序中执行一些多核多任务。user158 指出 Node.js 正在使用它。我对此一无所知。但是,为什么要等待 Node.js 批准 JavaScript 所提供的功能。

Google for JavaScript 多线程而不是 Node.js 多线程。您将了解 Web Workers、Promises 和其他内容。

于 2018-10-17T16:27:48.827 回答
0

你不能在 node.js 中本地运行多个线程,但是如果你真的需要从主线程中卸载一些代码,你总是可以使用child_process fork()它自己的 PID 和内存在另一个进程中运行一些代码。

于 2021-12-16T17:11:16.510 回答