合并较大数据的有效替代方法。框架 R

Posted

技术标签:

【中文标题】合并较大数据的有效替代方法。框架 R【英文标题】:Efficient alternatives to merge for larger data.frames R 【发布时间】:2012-06-24 04:59:00 【问题描述】:

我正在寻找一种有效的(计算机资源方面和学习/实施方面)方法来合并两个较大的(大小>100 万/300 KB RData 文件)数据帧。

base R 中的“merge”和 plyr 中的“join”似乎用尽了我所有的内存,导致我的系统崩溃。

示例 加载test data frame

试试

test.merged<-merge(test, test)

test.merged<-join(test, test, type="all")  
-

以下帖子提供了合并和替代方案的列表:How to join (merge) data frames (inner, outer, left, right)?

以下允许对象大小检查:https://heuristically.wordpress.com/2010/01/04/r-memory-usage-statistics-variable/

anonym产生的数据

【问题讨论】:

sql.df 还是 data.table? 在消化了下面的好回答后,我找到了:***.com/questions/4322219/…(虽然问题不是关于大 df 而是关于节省毫秒,但它确实得到了类似的答案,如下所示)。 【参考方案1】:

你必须在 R 中进行合并吗?如果没有,请使用简单的文件连接合并底层数据文件,然后将它们加载到 R 中。(我意识到这可能不适用于您的情况 - 但如果适用,它可以为您省去很多麻烦。)

【讨论】:

它必须在 R 中实时完成,因为它是优化例程中的一个步骤,写入磁盘可能会成为瓶颈。不过还是谢谢。【参考方案2】:

这是强制性的data.table 示例:

library(data.table)

## Fix up your example data.frame so that the columns aren't all factors
## (not necessary, but shows that data.table can now use numeric columns as keys)
cols <- c(1:5, 7:10)
test[cols] <- lapply(cols, FUN=function(X) as.numeric(as.character(test[[X]])))
test[11] <- as.logical(test[[11]])

## Create two data.tables with which to demonstrate a data.table merge
dt <- data.table(test, key=names(test))
dt2 <- copy(dt)
## Add to each one a unique non-keyed column
dt$X <- seq_len(nrow(dt))
dt2$Y <- rev(seq_len(nrow(dt)))

## Merge them based on the keyed columns (in both cases, all but the last) to ...
## (1) create a new data.table
dt3 <- dt[dt2]
## (2) or (poss. minimizing memory usage), just add column Y from dt2 to dt
dt[dt2,Y:=Y]

【讨论】:

感谢您的出色回答。我想如果您希望保持原始顺序,您可以添加一个 1:grow(df) 列并将其用作键的第一个元素? @EtienneLow-Décarie -- 这是个好问题。我认为您确实想添加这样的列,但 不要 使其成为键的元素。这样您就可以在任何时候使用它对数据进行重新排序。 (它不应该是键的一部分,因为它只是一个顺序标记,而不是在不同数据集中具有相同含义的变量/组标识符)。 data.table 是否意味着不再需要 apply 和 plyr!?令人印象深刻!【参考方案3】:

以下是 data.table 与 data.frame 方法的一些时间安排。 使用 data.table 非常快。关于内存,我可以非正式地报告这两种方法在 RAM 使用方面非常相似(在 20% 以内)。

library(data.table)

set.seed(1234)
n = 1e6

data_frame_1 = data.frame(id=paste("id_", 1:n, sep=""),
                          factor1=sample(c("A", "B", "C"), n, replace=TRUE))
data_frame_2 = data.frame(id=sample(data_frame_1$id),
                          value1=rnorm(n))

data_table_1 = data.table(data_frame_1, key="id")
data_table_2 = data.table(data_frame_2, key="id")

system.time(df.merged <- merge(data_frame_1, data_frame_2))
#   user  system elapsed 
# 17.983   0.189  18.063 


system.time(dt.merged <- merge(data_table_1, data_table_2))
#   user  system elapsed 
#  0.729   0.099   0.821 

【讨论】:

以上是关于合并较大数据的有效替代方法。框架 R的主要内容,如果未能解决你的问题,请参考以下文章

在 R 中有效地设置非常大的数据帧

大数据-Hadoop生态(19)-MapReduce框架原理-Combiner合并

按行名合并 R 中超过 2 个数据框

在R中的几列中获取月度均值的有效方法

python 数据较大 性能分析

R读取大型数据集内存不足如何解决,如果利用Linux有啥有效方法吗?