【问题标题】:R large distance matrix in vegan素食主义者中的R大距离矩阵
【发布时间】:2016-03-20 12:42:25
【问题描述】:

我在具有 128 GB RAM 的机器上运行 R 3.2.3。我有一个 123028 行 x 168 列的大矩阵。我想在 R 中使用层次聚类算法,因此在此之前,我尝试使用 vegan 包中的 vegdist() 函数和 Bray-Curtis 方法在 R 中创建一个距离矩阵。我收到有关内存分配的错误:

df <- as.data.frame(matrix(rnorm(20668704), nrow = 123028))
library(vegan)
mydist <- vegdist(df)

vegdist(df) 中的错误: .Fortran 不支持长向量(参数 4)

如果我使用 pryr 包找出距离矩阵需要多少内存,我发现需要 121 GB,这比我拥有的 RAM 少。

library(pryr)
mem_change(x <- 1:123028^2)

121 GB

我知道 R 中的单个对象曾经有 20 亿个值的限制,但我认为该限制在最新版本的 R 中消失了。还有其他我不知道的内存限制吗?

底线是我想知道:我能做些什么来处理这个错误?真的是因为内存限制还是我错了?我想留在R中并使用除k-means之外的聚类算法,所以我需要计算一个距离矩阵。

【问题讨论】:

  • 你总是可以分段计算。

标签: r memory hierarchical-clustering vegan


【解决方案1】:

R 可以很好地处理长向量,但似乎距离矩阵计算是在 C 或 Fortran 中实现的,并使用 .C.Fortran 与 R 接口,它们不接受长向量(即具有长度的向量> 2^32 -1) 作为参数。请参阅文档here,其中指出:

请注意,.C 和 .Fortran 接口不接受长向量, 所以必须使用 .Call (或类似的)。

查看vegdist() 函数的source code,看起来您的矩阵正在转换为向量,然后传递给用C 实现的函数以计算距离。相关代码行:

d <- .C("veg_distance", x = as.double(x), nr = N, nc = ncol(x), 
        d = double(N * (N - 1)/2), diag = as.integer(FALSE), 
        method = as.integer(method), NAOK = na.rm, PACKAGE = "vegan")$d

这就是你的问题。当您的矩阵转换为向量时,它会变成一个长向量,.C 不支持。您将不得不寻找一个不同的包来计算您的距离矩阵(或自己实现一个)。

【讨论】:

  • 谢谢!这确实回答了我为什么会收到错误的问题。我的下一个问题是我能做些什么呢?我可以尝试按照上面 Alex 的建议分段进行,但是否还有其他现有函数可以计算更大矩阵上的 Bray-Curtis 距离?
  • @jk22 作为第一步,您应该联系素食作者。他们对我的经验非常有帮助,并且可能能够找到可以纳入未来素食版本的解决方案。
  • @jk22 进行快速 google 搜索会生成 ecodist 包,该包具有 bcdist() 函数来计算 Bray-Curtis 距离。我不确定它是否可以处理更大的矩阵。
  • 另外,我会听从@Tyler 的建议,就您的问题联系素食作者,以便问题得到解决。
  • 我在这里(素食主义者)。分析是正确的:vegdist() 不处理长向量。我没有计划改变这一点,因为我没有硬件可以使用长向量(内存首先耗尽),但我会欢迎修复(素食主义者在 github 中)。函数 designdist 是纯 R 语言,可以处理长向量,但它使用更多内存用于临时对象(多 3 倍)。同样,dist(x, "manhattan")/as.dist(outer(rowSums(x), rowSums(x), "+")) 是 Bray-Curtis,但将内存用于临时对象。此外,您所做的任何事情都需要大量的 CPU 时间:这一切都值得吗?
猜你喜欢
  • 2022-01-12
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2016-12-29
  • 1970-01-01
  • 2013-06-20
  • 2013-06-12
相关资源
最近更新 更多