Node.js多线程编程使用线程

3
我正在使用nodejs执行一个CPU密集型任务,基本上生成大量数据并将其存储在文件中。对于单个类型的数据,我正在将数据流式传输到输出文件中。
目标:我想并行生成多种类型的数据(充分利用我的多核CPU),而不是每个进程都有自己的堆内存。从而提供更大的进程内存和增加执行速度。
我计划使用node fibers来处理回调,这也是meteor js所使用的。但我不确定这是否能实现我的目标,因为在Chris Mather制作的meteor fibers视频中,最终所有内容都是单线程的,并且node fibers以某种方式管理同一单线程事件循环以提供其功能。
所以,
  • 这是否意味着,如果我使用Node Fibers,我将不会并行运行我的任务,因此无法利用我的CPU核心?

  • Node webworker-threads 是否能帮助我实现所需的功能。正如模块主页上所述,WebWorker线程将在单独/并行的CPU进程中运行,从而真正提供多线程?

  • 最后一个问题是,这是否意味着Node.js不适合这样的CPU密集型任务?

注:我不想使用被呈现为线程的异步代码结构库,但实际上只是在同一异步代码上添加语法糖,因为任务大部分是CPU密集型的。我已经尽可能地使用了异步功能。

// 更新1(基于群集的答案)

抱歉,我忘记提到的是,我遇到的群集问题是:

  • 复杂的负载均衡使我拥有的工作量以一种确保特定的一组并行任务在某些其他任务之前执行的方式执行。

  • 不确定集群是否真正实现了我想要的,参考webworker-threads npm首页上的这些行

"不能阻塞事件循环"问题是Node事件模型固有的问题。无论您运行多少个Node进程作为Node集群,它都无法解决CPU绑定任务的问题。

.....任何关于如何解决这个问题的建议都会有帮助。

1个回答

3

与其尝试实现多线程,使用多个进程在Node.js中会更加容易。

例如,可以使用cluster模块。这使您可以轻松地在多个进程中运行相同的js代码,例如每个核心一个进程,并收集它们的结果/在完成时被通知。

如果cluster提供的功能超出了您的需求,那么您也可以直接调用fork


如果你需要线程并行而不是进程,并且想要编写一个async native模块,那么你可以考虑使用libuv线程池(虽然阻塞它可能会降低I/O性能),或者按照自己的意愿分叉线程(但这样一来,你必须自己同步与Node的其余部分)。

更新后1

对于负载均衡,如果集群不适用于您,则可以像我提到的那样使用fork自己完成。集群的源代码可用。

对于另一点,这意味着如果任务确实是CPU密集型的,那么除了在其他所有技术都使用Node的情况下更简单之外,Node不会给您带来任何优势。您唯一的选择是确保您正在使用所有可用的CPU资源,这将由工作进程池提供。如果您已经在使用Node,则最简单的选项是使用它已经拥有的选项(cluster或libuv)。如果它们不足够,则需要找到其他东西。

无论使用什么技术,多进程并行比多线程并行要容易得多。

注意:尽管您所说的话不正确,但您绝对需要使用异步代码,因为它是CPI密集型的,否则您的任务将阻塞所有I/O。您不希望发生这种情况。


这是否意味着在Node中没有任何库可以提供多线程并行性,与其他技术相比? - damitj07
有一些,但在很多人的看法中它们是一个非常糟糕的想法。JavaScript 并不是为此而设计的。 - OrangeDog
webworker-threads npm模块怎么样?我关心的一个问题是它所说的声明,即集群仍然会导致节点事件循环变慢,不会帮助加速...? - damitj07
1
一些通用建议:在测试你的确切用例之前,不要相信任何人对性能的陈述。如果你的服务器只有1个核心处于100%的状态,而其他15个核心没有工作,同时所有的I/O都在等待数据,我敢肯定你会看到速度提升。 - OrangeDog
那么你的意思是,我最好使用聚类而不是多线程? - damitj07
显示剩余3条评论

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接