按列绑定几个大矩阵

Posted

技术标签:

【中文标题】按列绑定几个大矩阵【英文标题】:Binding several large matrices by column 【发布时间】:2015-09-22 11:19:36 【问题描述】:

我真的知道“大矩阵问题”是这里经常出现的话题,但我想详细解释一下我关于大矩阵的具体问题。

严格来说,我想cbind R 中具有特定名称模式的几个大型矩阵。下面的代码显示了我到目前为止的最佳尝试。

首先让我们生成文件来模拟我的真实矩阵:

# The df1
df1 <- '######## infx infx infx
######## infx infx infx
probeset_id sample1 sample2 sample3
PR01           1       2       0
PR02           -1      2       0
PR03            2      1       1
PR04           1       2       1
PR05           2       0       1'
df1 <- read.table(text=df1, header=T, skip=2)
write.table(df1, "df1.txt", col.names=T, row.names=F, quote=F, sep="\t")

# The df2 
df2 <- '######## infx infx infx
######## infx infx infx
probeset_id sample4 sample5 sample6
PR01           2       2       1
PR02           2      -1       0
PR03            2      1       1
PR04           1       2       1
PR05           0       0       1'
df2 <- read.table(text=df2, header=T, skip=2)
write.table(df2, "df2.txt", col.names=T, row.names=F, quote=F, sep="\t")

# The dfn 
dfn <- '######## infx infx infx
######## infx infx infx
probeset_id samplen1 samplen2 samplen3
PR01           2       -1       1
PR02           1      -1       0
PR03            2      1       1
PR04           1       2       -1
PR05           0       2       1'
dfn <- read.table(text=dfn, header=T, skip=2)
write.table(dfn, "dfn.txt", col.names=T, row.names=F, quote=F, sep="\t")

然后将其导入 R 并按照我的预期写入output 文件:

### Importing and excluding duplicated 'probeset_id' column
calls = list.files(pattern="*.txt")
library(data.table)
calls = lapply(calls, fread, header=T)
mycalls <- as.data.frame(calls)
probenc <- as.data.frame(mycalls[,1])
mycalls <- mycalls[, -grep("probe", colnames(mycalls))]
output <- cbind(probenc, mycalls)
names(output)[1] <- "probeset_id"
write.table(output, "output.txt", col.names=T, row.names=F, quote=F, sep="\t")

输出的样子:

> head(output)
  probeset_id sample1 sample2 sample3 sample4 sample5 sample6 samplen1 samplen2 samplen3
1        PR01       1       2       0       2       2       1        2       -1        1
2        PR02      -1       2       0       2      -1       0        1       -1        0
3        PR03       2       1       1       2       1       1        2        1        1
4        PR04       1       2       1       1       2       1        1        2       -1
5        PR05       2       0       1       0       0       1        0        2        1

此代码非常适合我想要做的事情,但是,我使用我的真实数据(超过 30 个“df”对象,每个对象约 1.3GB 或/和 600k 行乘以 100 列)面临着已知的 R 内存限制)。

我读到了一个非常有趣的 SQL 方法 (R: how to rbind two huge data-frames without running out of memory),但我对 SQL 缺乏经验,并且没有找到一种方法来适应我的情况。

干杯,

【问题讨论】:

【参考方案1】:

我之前误解了这个问题;现在评论说清楚了。然后你需要使用像ff 这样的包。这使您可以处理硬盘中的文件,而不是将它们加载到 RAM 中。当您提到 RAM 不足以加载系统中的所有文件时,这看起来像是您的问题的解决方案。

首先用read.table.ffdf加载文件,然后使用下面的cbind它们:

#load files in R
library(ff)

df1 <- read.table.ffdf('df1.txt', header=T, skip=2)
df2 <- read.table.ffdf('df2.txt', header=T, skip=2)
dfn <- read.table.ffdf('dfn.txt', header=T, skip=2)

然后像这样合并:

mergedf <- do.call('ffdf', c(physical(df1), physical(df2), physical(dfn)))

不幸的是,我不能使用您的示例,因为 read.table.ffdf 不支持 text 参数,但以上应该可以。 ff 包有自己的(不是很复杂)语法,您可能需要熟悉它,因为它适用于硬盘上的文件。例如,apply 函数是使用 ffapply 函数完成的,其方式与 apply 几乎相同。

查看here、here 和here 以获取有关包ff 的一些基本教程。

您还可以查看包内的功能并使用内置帮助来帮助自己处理ls(package:ff)

【讨论】:

主要问题是在将所有大矩阵读入 R 环境之前,我的内存崩溃了。这就是为什么我编写代码来生成这 3 个“df”文本文件。我真正的问题是如何在不耗尽内存的情况下创建一个连续文件(作为我的 output.txt)。 既然我已经理解了这个问题,我已经用推荐的解决方案更新了答案。

以上是关于按列绑定几个大矩阵的主要内容,如果未能解决你的问题,请参考以下文章

R语言创建使用矩阵(按行按列填充,矩阵命名,矩阵下标使用,数据框转换为矩阵)

对矩阵按行和按列进行排序

按列而不是行存储矩阵[重复]

# 零基础入门矩阵

r语言如何生成矩阵偶数

在r中按多列排序矩阵