NodeJS使用cluster,进程间如何共享一个大的数组(比如4GB的数据)
发布于 10 年前 作者 hainee 13424 次浏览 最后一次编辑是 8 年前

不要读文件,那样IO压力太大了……

31 回复

这么大的数组就应该放数据库里

v8已经限制了nodejs每个进程最大内存上限最多就是1个多G,如果你的需求就是4个G的话,那就别想了

你只有把这块数据的读写封装成外部服务,通过tcp或socket来读写,比如redis实际上就可以看作进程间共享内存数据的一个形式

4G内存的数据可以在Node.js实现的,buffer的内存管理不受V8限制的

还有一种糙快猛的搞法,把4G内存虚拟成硬盘,把文件放到虚拟盘里,用标准的fs api访问 这个办法是我乱想的,后果自负哈

@snoopy 数据就是从数据库独取出来的,buffer能在进程间共享? @yeaha NodeJS如何虚拟内存成文件?

需要持久 === mongodb 不用持久 === redis 4G都放在nodejs,压力山大

一次从数据库读4G的数据,你确定你的应用流程或者算法没问题?是不是可以再优化一下?

4G数据就大了啊?小伙伴们,木有解决方案么?

smalloc我没看到进程间如何共享使用啊! 比如有没有这样的库

var shm = require(“shm”);//假设有这么一个库 if(cluster.isMaster) { //在这里创建bigData shm.create(“bigData”, [……]);//至少4GB的数据 for(var i=0;i<=10;i++) { cluster.fork(); } } else { //在这里使用bigData var bigData = shm.get(“bigData”);//bigData指向create中创建的那个数组 //在这里使用…… }

@hainee 你理解cluster.fork的原理么? fork出来的进程都是独立的.进程之间共享这么大的内存数据不现实,非数据库或memcached莫属

搞一个独立的node进程,里边只放这个数组,开socket服务,提供操作数组的接口 其他进程通过socket操作数组

这样还不如用把数组分拆,用redis存(redis键值有大小限制),我觉得这样才是最好的,用持久化数据库要读硬盘太慢了

@dlutwuwei 内存足够大的话, mongodb 就基本不需要读写硬盘了,变成类内存型数据库

用内存数据库保存就行了,像Redis, MongoDB内存表,MySQL内存表

@j4cnodejs 正因为知道fork的原理,所以才需要一个库来提供跨进程操作大数据的功能啊!

我知道有内存数据库,但是我想在NodeJS中原生实现集群对大数据内存的访问

晕了,现在也遇到类似的问题,求解决方案。

另外请教楼主,如果是key-value缓存,用一个大的对象来进行,性能上会不会有什么问题?

例如这样的对象: cache_obj = { key1: value1, key2:value2, ... 上百万这样的键值对... }

然后需要的时候直接读取: cache_obj[‘key1’],有没有更好的缓存数据供高性能访问?

自己实现吧,用node addon封装一下boost的Shared Memory。但是即便如此,想直接将共享内存作为数组来用,也不会太方便。毕竟V8的数组是被V8自己的垃圾回收所管理的。

一定要数据达到4G才能共享吗?这样做是不是有些死磕的感觉。:)

哎哟,自己封装shm算了,写好了开源吧

我就想问下 没有楼主说的那么大的数组 进程间该如何共享?

@xiaohuame 我们教操作系统的老师八年前刚教了这节课。 管道 命名管道 IPC 消息队列 信号量 共享内存 套接字

方法多多任君选择,总有一款适合你

@jiangzhuo 就nodejs cluster的IPC共享数据呢?如何将主进程中的数据返回给子进程呢

cluster.send 的数据,有大小限制吗?

@yakczh 有没有,都不能这样玩

@i5ting 为啥不能这么玩

@jiangzhuo 姿势不对,哈哈

@i5ting 我看了官方文档上进程间都是通过on('message')process.send({})去传递消息和接受消息的,怎么姿势就不对了呢

需要支持跨服务器间调用么

回到顶部