gpt4 book ai didi

r - 高效构建大型(200 MM 线)数据框

转载 作者:行者123 更新时间:2023-12-04 22:46:13 25 4
gpt4 key购买 nike

我正在尝试在 R 中构建一个大型(~200 MM 行)数据帧。数据帧中的每个条目将包含大约 10 位数字(例如 1234.12345)。该代码旨在遍历一个列表,从 [i] 之后的每个项目中减去位置 [i] 中的一个项目,而不是 [i] 之前的项目(如果我将输出放入矩阵,它将是一个三角矩阵)。代码很简单,在较小的列表上运行良好,但我想知道是否有更快或更有效的方法来做到这一点?我认为答案的第一部分将涉及“不要使用嵌套的 for 循环”,但我不确定替代方案是什么。

这个想法是,这将是社交网络分析图的“边缘列表”。一旦我有了“outlist”,我将根据一些标准(<、>、==、)减少边的数量,这样最终的列表(和图表)就不会那么沉重了。

#Fake data of same approximate dimensions as real data
dlist<-sample(1:20,20, replace=FALSE)
#purge the output list before running the loop
rm(outlist)
outlist<-data.frame()

for(i in 1:(length(dlist)-1)){
for(j in (i+1):length(dlist)){

outlist<-rbind(outlist, c(dlist[i],dlist[j], dlist[j]-dlist[i]))

}
}

最佳答案

IIUC 你的最终数据集将是约 2 亿行×3 列,所有类型都是 numeric ,其总空间为:

200e6 (rows) * 3 (cols) * 8 (bytes) / (1024 ^ 3)
# ~ 4.5GB

这是一个相当大的数据,必须尽可能避免复制。

这是一个使用 data.table 的方法包未导出(内部) vecseq函数(用 C 编写,速度快 + 内存效率高)并通过引用运算符 := 使用它的赋值, 避免复制。
fn1 <- function(x) {
require(data.table) ## 1.9.2
lx = length(x)
vx = as.integer(lx * (lx-1)/2)
# R v3.1.0 doesn't copy on doing list(.) - so should be even more faster there
ans = setDT(list(v1 = rep.int(head(x,-1L), (lx-1L):1L),
v2=x[data.table:::vecseq(2:lx, (lx-1L):1, vx)]))
ans[, v3 := v2-v1]
}

基准测试:

我将使用其他答案中关于您的数据维度的函数进行基准测试。请注意,我的基准测试是在 R v3.0.2 上,但是 fn1()应该在 R v3.1.0 上提供更好的性能(速度和内存),因为 list(.)不再导致复制。
fn2 <- function(x) {
diffmat <- outer(x, x, "-")
ss <- which(upper.tri(diffmat), arr.ind = TRUE)
data.frame(v1 = x[ss[,1]], v2 = x[ss[,2]], v3 = diffmat[ss])
}

fn3 <- function(x) {
idx <- combn(seq_along(x), 2)
out2 <- data.frame(v1=x[idx[1, ]], v2=x[idx[2, ]])
out2$v3 <- out2$v2-out2$v1
out2
}

set.seed(45L)
x = runif(20e3L)
system.time(ans1 <- fn1(x)) ## 18 seconds + ~8GB (peak) memory usage
system.time(ans2 <- fn2(x)) ## 158 seconds + ~19GB (peak) memory usage
system.time(ans3 <- fn3(x)) ## 809 seconds + ~12GB (peak) memory usage

请注意 fn2()由于使用 outer需要相当多的内存(峰值内存使用 >=19GB)并且比 fn1() 慢. fn3()只是非常非常慢(由于 combn 和不必要的副本)。

关于r - 高效构建大型(200 MM 线)数据框,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24469035/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com