5

我正在尝试更深入地研究 R 例程的并行化。

关于一堆“工人”进程的沟通,我有什么选择

  1. 各个工人之间的沟通?
  2. 工人与“主人”进程的沟通?

AFAIU,没有主进程和所有工作进程都可以访问的“共享环境/共享内存”,对吧?

到目前为止,我想出的最好的想法是将通信建立在读取和写入 JSON 文档到硬盘驱动器的基础上。这可能是个坏主意;-) 我选择.json.Rdata文件,因为 JSON 似乎经常用于软件间通信,所以我想采用那个“标准”。

期待学习更好的选择!

仅供参考:我通常基于基础包parallel和contrib包snowfall的功能进行并行化,主要依靠功能sfClusterApplyLB()来完成工作

编辑

我应该说我在 Windows 上运行,但也非常感谢基于 Linux 的答案/提示!

4

2 回答 2

5

正如CRAN Task View for High-Performance Computing中详述的那样,Norm Matloff的Rdsm包提供共享内存通信。

于 2012-07-20T16:08:57.353 回答
5

对于进程之间的通信,一种有趣的起点是帮助页面?socketConnections和块中标记为“## Not run:”的代码。所以启动一个R进程并运行

 con1 <- socketConnection(port = 6011, server=TRUE)

该进程充当服务器,在特定端口上侦听某些信息。现在启动第二个 R 进程并输入

 con2 <- socketConnection(Sys.info()["nodename"], port = 6011)

进程 2 中的 con2 与进程 1 上的 con1 建立了套接字连接。回到 con1,写出 R 对象LETTERS

writeLines(LETTERS, con1)

并在 con2 上检索它们。

readLines(con2)

因此,您无需写入磁盘即可在进程之间进行通信。这里也隐含了一些重要的概念,例如,关于阻塞与非阻塞连接。它不限于同一台机器上的通信,只要这些端口可以通过计算机所在的任何网络访问。这是makePSOCKclusterparallel包中的基础,另外进程1实际上使用systemparallel包中的命令和脚本来启动进程2。返回的对象makePSOCKcluster是可子设置的,因此您可以将一小部分用于集群以解决特定任务。原则上,您可以安排生成的节点相互通信,而与生成的节点无关。

parallel一个有趣的练习是使用包中的类似 fork 的命令(在非 Windows 上)来做同样的事情。帮助页面中有一个高级版本?mcparallel,例如,

 p <- mcparallel(1:10)
 q <- mcparallel(1:20)
 # wait for both jobs to finish and collect all results
 res <- mccollect(list(p, q))

但这建立在较低级别sendMaster和朋友之上(峰值mcparallelmccollect源代码)。

Rmpi 包采用类似于PSOCK示例的方法,其中管理器使用脚本生成工作人员,并使用 mpi 而不是套接字进行通信。mpi.comm.rank但是,如果您有一个正常运行的 MPI 实现,那么值得一个周末项目的另一种方法是实现一个脚本,该脚本对不同的数据进行相同的计算,然后使用诸如、mpi.barriermpi.send.Robj和之类的命令将结果整理到单个节点上mpi.recv.Robj

一个有趣的周末项目将使用并行包来实现一个涉及并行计算但不属于 mclapply 种类的工作流程,例如,一个进程从网站收集数据,然后将其传递给另一个绘制漂亮图片的进程。第一个进程的输入很可能是 JSON,但 R 中的通信可能更适合 R 数据对象。

于 2012-07-20T21:39:19.557 回答