我一直在这个网站上阅读,但没有找到确切的答案。如果它已经存在,我为重新发布道歉。
我正在处理非常大的数据集(在具有32 GB RAM的计算机上有6亿行,64列)。我真的只需要这些数据的小得多的子集,但除了简单地用fread导入一个数据集并选择我需要的5列之外,我还在努力执行任何功能。之后,我尝试用我需要的特定条件覆盖我的数据集,但是我点击我的RAM上限并得到消息"错误:无法分配4.5 GB的矢量大小。我看了ff和bigmemory包作为替代品,但看起来你可以在导入这些包之前进行子集化?除了升级计算机上的RAM之外,还有解决这个问题的方法吗?
我正在尝试执行的任务:
>SampleTable<-fread("my.csv", header = T, sep = ",", select=c("column1", "column2", "column7", "column12", "column15"))
>SampleTable2<-SampleTable[SampleTable[,column1=="6" & column7=="1"]]
此时,我打了我的记忆帽。尝试使用另一个包但导入所有64列6亿行会更好吗?我也不想花几个小时来执行一次导入。
答案 0 :(得分:2)
如果您的数据集可以轻松解析(例如没有嵌入式逗号):
library(data.table)
> fread('cat tmp.csv')
col1 col2 col3 col4 col5 col6 col7 col8 col9 col10 col11 col12 col13 col14 col15 col16 col17
1: 6 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1
2: 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2
> fread("cat tmp.csv | awk -F ',' 'NR == 1 || ($1 == 6 && $7 == 1)'")
col1 col2 col3 col4 col5 col6 col7 col8 col9 col10 col11 col12 col13 col14 col15 col16 col17
1: 6 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1
> fread("cat tmp.csv | awk -F ',' 'NR == 1 || ($1 == 6 && $7 == 1) {print $1, $2, $7, $12, $15}'")
col1 col2 col7 col12 col15
1: 6 1 1 1 1
>
答案 1 :(得分:1)
您可以做的是以块的形式阅读CSV文件:
# Define only the subset of columns
csv <- "my.csv"
colnames <- names(read.csv(csv, header = TRUE, nrows = 1))
colclasses <- rep(list(NULL), length(colnames))
ind <- c(1, 2, 7, 12, 15)
colclasses[ind] <- "double"
# Read header and first line
library(dplyr)
l_df <- list()
con <- file(csv, "rt")
df <- read.csv(con, header = TRUE, nrows = 1, colClasses = colclasses) %>%
filter(V1 == 6, V7 == 1)
names(df) <- paste0("V", ind)
l_df[[i <- 1]] <- df
# Read all other lines and combine
repeat {
i <- i + 1
df <- read.csv(con, header = FALSE, nrows = 9973, colClasses = colclasses)
l_df[[i]] <- filter(df, V1 == 6, V7 == 1)
if (nrow(df) < 9973) break
}
df <- do.call("rbind", l_df)
9973
是一个任意素数,几乎没有机会成为nlines - 1
的除数。