将多个单列文本文件(不同长度)读取到文件名为列 header 的数据框

Read multiple single column text files (varying length) to data frame where filename is column header

我有很多 (600+) 个文本文件,每个文件只包含一列数据,我想将这些数据读入 R 中的数据框中。要注意的是,我需要将每个文件中的值导入为一个单独的列,每个文件中的值数量不相等。文本文件都以我不需要的标题 'Area' 开头(我试图将文件名设置为 header ),然后继续处理一列数字(4000 - 10000 值)例如

Area
0.0034556
0.0002345
....

我最接近的是:

filenames <-dir()
n <- length(filenames)
for (i in 1:n) {data[i] <- read.csv(filenames[i]}
## printing data at this point gives lists for each value of i

然后我尝试将包含列表的值绑定到文件名以用作单独的列(在变量 c 下)然后我希望将单独的列拼凑成一个数据框:

for (i in 1:n) {c[i] <- rbind(filenames[i], data[i])}

当打印 c 时,这似乎给出了一个包含两个元素的列表 - 最后一个文件的名称和它包含的值的数量。

我担心,即使我可以将使用 read.csv 导入的列表绑定到 headers 列,我仍然无法将其组合到数据框中,因为值的数量因文件而异。我已经看到了将多个文本文件的值合并到一个列中的可能解决方案(并且已经开始工作) - 但是找不到解决这个问题的方法,因为每个导入的文件都需要在线或漩涡中有自己的列。

如有任何帮助,我将不胜感激! 安格斯

可能最简单的方法就是将所有内容都放在一个列表中。在函数 read.csv 中,您可以立即使用 col.names.

定义列名
filenames <-dir()
n <- length(filenames)
data <- list()
for (i in 1:n) {data[[i]] <- read.csv(filenames[i], col.names = filenames[i])}

由于数据量较大建议使用data.table.

第 1 步:一次读取所有文件data.table

library(data.table)
filenames <-dir()
dt_long <- rbindlist(setNames(lapply(filenames, fread), filenames), idcol = TRUE)
dtl
#         .id      Area
#1: file1.csv 0.0034556
#2: file1.csv 0.0002345
#3: file2.csv 0.0034556
#4: file2.csv 0.0002345
#5: file2.csv 0.0034556
#6: file2.csv 0.0002345
#7: file2.csv 0.0034556
#8: file2.csv 0.0002345

fread 读取 lapply 调用中的每个文件。 lapply 是一种隐含的文件名循环,returns 是一个列表,其中每个列表元素包含一个 data.table 和一个文件的内容。

setNames用于将每个列表元素重命名为相应的文件名。

最后,rbindlist将列表中的单个data.tables合并为一个大的data.table。每行的起点由 .id col.

标识

第 2 步:整形为宽幅面

通常,我更喜欢使用长格式的数据,因为我可以使用分组函数(例如,data.table 语法中的 by = .id)同时影响所有文件的数据。

但是,如果您坚持为每个文件设置一个单独的列,您可以将宽格式重新调整为长格式:

dt_wide <- dcast(dt_long, rowid(.id) ~ .id, value.var = "Area")
dt_wide
#   .id file1.csv file2.csv
#1:   1 0.0034556 0.0034556
#2:   2 0.0002345 0.0002345
#3:   3        NA 0.0034556
#4:   4        NA 0.0002345
#5:   5        NA 0.0034556
#6:   6        NA 0.0002345

请注意,由于文件大小不同而导致的缺失值已由 NA 填补。

数据

为了有一个可重现的例子,我创建了两个虚拟数据文件

file1.csv

Area
0.0034556
0.0002345

file2.csv

Area
0.0034556
0.0002345
0.0034556
0.0002345
0.0034556
0.0002345