R导入具有不同初始行数的文件以跳过
R Import files with differing number of initial rows to skip
我需要将许多文件读入 R,做一些清理,然后将它们组合成一个数据框。文件基本上都是这样开头的:
=~=~=~=~=~=~=~=~=~=~=~= PuTTY log 2016.07.11 09:47:35 =~=~=~=~=~=~=~=~=~=~=~=
up
Upload #18
Reader: S1 Site: AA
--------- upload 18 start ---------
Type,Date,Time,Duration,Type,Tag ID,Ant,Count,Gap
E,2016-07-05,11:45:44.17,"upload 17 complete"
D,2016-07-05,11:46:24.69,00:00:00.87,HA,900_226000745055,A2,8,1102
D,2016-07-05,11:46:43.23,00:00:01.12,HA,900_226000745055,A2,10,143
第 headers 列的行是 "Type,Date,Time,Duration,Type,Tag ID,Ant,Count,Gap"
。数据应该有 9 列。问题是 header 字符串上方的行数对于每个文件都是不同的,所以我不能简单地使用 skip = 5。我也只需要以 "D,"
开头的行,其他都是消息,不是数据。
读取文件的最佳方式是什么,确保我有 9 列并跳过所有垃圾?
我一直在使用 readr()
包中的 read_csv
函数,因为到目前为止它产生的格式问题最少。但是,我对任何新想法都持开放态度,包括一种只阅读以 "D,"
开头的行的方法。我试过使用 read.table
和 skip = grep("Type," readLines(i))
,但它似乎没有正确找到 header 字符串。这是我的基本代码:
dataFiles <- Sys.glob("*.*")
datalist <- list()
for (i in dataFiles) {
d01 <- read_csv(i, col_names = F, na = "NA", skip = 35)
# do clean-up stuff
datalist[[i]] <- d
}
如果您的 header 行始终以单词 Type
开头,您可以简单地从初始读取中省略 skip
选项,然后删除 [=18] 之前的任何行=]行。下面是一些帮助您入门的代码(未测试):
dataFiles <- Sys.glob("*.*")
datalist <- list()
for (i in dataFiles) {
d01 <- read_csv(i, col_names = F, na = "NA")
headerRow <- which( d01[,1] == 'Type' )
d01 <- d01[headerRow+1,] # This keeps all rows after the header row.
# do clean-up stuff
datalist[[i]] <- d
}
如果你想保留header,你可以使用:
for (i in dataFiles) {
d01 <- read_csv(i, col_names = F, na = "NA")
headerRow <- which( d01[,1] == 'Type' )
d01 <- d01[headerRow+1,] # This keeps all rows after the header row.
header <- d01[headerRow,] # Get names from header row.
setNames( d01, header ) # Assign names.
# do clean-up stuff
datalist[[i]] <- d
}
您可以使用自定义函数遍历每个文件,并仅过滤 type
列中以 D
开头的文件,并在末尾将它们全部绑定在一起。如果您希望将它们作为单独的列表,请删除 bind_rows
。
load_data <-function(path) {
require(dplyr)
setwd(path)
files <- dir()
read_files <- function(x) {
data_file <- read.csv(paste(path, "/", x, ".csv", sep = ""), stringsAsFactors = FALSE, na.strings=c("","NA"))
row.number <- grep("^Type$", data_file[,1])
colnames(data_file) <- data_file[row.number,]
data_file <- data_file[-c(1:row.number+1),]
data_file <- data_file %>%
filter(grepl("^D", Type))
return(data_file)
}
data <- lapply(files, read_files)
}
list_of_file <- bind_rows(load_data("YOUR_FOLDER_PATH"))
另一个基本的 R 解决方案如下:您按行读入文件,获取以 "D" 和 header 行开头的行的索引。之后,您只需将这些行用“,”分隔并将其放入 data.frame 并将 header 行中的名称分配给它。
lines <- readLines(i)
dataRows <- grep("^D,", lines)
names <- unlist(strsplit(lines[grep("Type,", lines)], split = ","))
data <- as.data.frame(matrix(unlist(strsplit(lines[dataRows], ",")), nrow = length(dataRows), byrow=T))
names(data) <- names
输出:
Type Date Time Duration Type Tag ID Ant Count Gap
1 D 2016-07-05 11:46:24.69 00:00:00.87 HA 900_226000745055 A2 8 1102
2 D 2016-07-05 11:46:43.23 00:00:01.12 HA 900_226000745055 A2 10 143
我需要将许多文件读入 R,做一些清理,然后将它们组合成一个数据框。文件基本上都是这样开头的:
=~=~=~=~=~=~=~=~=~=~=~= PuTTY log 2016.07.11 09:47:35 =~=~=~=~=~=~=~=~=~=~=~=
up
Upload #18
Reader: S1 Site: AA
--------- upload 18 start ---------
Type,Date,Time,Duration,Type,Tag ID,Ant,Count,Gap
E,2016-07-05,11:45:44.17,"upload 17 complete"
D,2016-07-05,11:46:24.69,00:00:00.87,HA,900_226000745055,A2,8,1102
D,2016-07-05,11:46:43.23,00:00:01.12,HA,900_226000745055,A2,10,143
第 headers 列的行是 "Type,Date,Time,Duration,Type,Tag ID,Ant,Count,Gap"
。数据应该有 9 列。问题是 header 字符串上方的行数对于每个文件都是不同的,所以我不能简单地使用 skip = 5。我也只需要以 "D,"
开头的行,其他都是消息,不是数据。
读取文件的最佳方式是什么,确保我有 9 列并跳过所有垃圾?
我一直在使用 readr()
包中的 read_csv
函数,因为到目前为止它产生的格式问题最少。但是,我对任何新想法都持开放态度,包括一种只阅读以 "D,"
开头的行的方法。我试过使用 read.table
和 skip = grep("Type," readLines(i))
,但它似乎没有正确找到 header 字符串。这是我的基本代码:
dataFiles <- Sys.glob("*.*")
datalist <- list()
for (i in dataFiles) {
d01 <- read_csv(i, col_names = F, na = "NA", skip = 35)
# do clean-up stuff
datalist[[i]] <- d
}
如果您的 header 行始终以单词 Type
开头,您可以简单地从初始读取中省略 skip
选项,然后删除 [=18] 之前的任何行=]行。下面是一些帮助您入门的代码(未测试):
dataFiles <- Sys.glob("*.*")
datalist <- list()
for (i in dataFiles) {
d01 <- read_csv(i, col_names = F, na = "NA")
headerRow <- which( d01[,1] == 'Type' )
d01 <- d01[headerRow+1,] # This keeps all rows after the header row.
# do clean-up stuff
datalist[[i]] <- d
}
如果你想保留header,你可以使用:
for (i in dataFiles) {
d01 <- read_csv(i, col_names = F, na = "NA")
headerRow <- which( d01[,1] == 'Type' )
d01 <- d01[headerRow+1,] # This keeps all rows after the header row.
header <- d01[headerRow,] # Get names from header row.
setNames( d01, header ) # Assign names.
# do clean-up stuff
datalist[[i]] <- d
}
您可以使用自定义函数遍历每个文件,并仅过滤 type
列中以 D
开头的文件,并在末尾将它们全部绑定在一起。如果您希望将它们作为单独的列表,请删除 bind_rows
。
load_data <-function(path) {
require(dplyr)
setwd(path)
files <- dir()
read_files <- function(x) {
data_file <- read.csv(paste(path, "/", x, ".csv", sep = ""), stringsAsFactors = FALSE, na.strings=c("","NA"))
row.number <- grep("^Type$", data_file[,1])
colnames(data_file) <- data_file[row.number,]
data_file <- data_file[-c(1:row.number+1),]
data_file <- data_file %>%
filter(grepl("^D", Type))
return(data_file)
}
data <- lapply(files, read_files)
}
list_of_file <- bind_rows(load_data("YOUR_FOLDER_PATH"))
另一个基本的 R 解决方案如下:您按行读入文件,获取以 "D" 和 header 行开头的行的索引。之后,您只需将这些行用“,”分隔并将其放入 data.frame 并将 header 行中的名称分配给它。
lines <- readLines(i)
dataRows <- grep("^D,", lines)
names <- unlist(strsplit(lines[grep("Type,", lines)], split = ","))
data <- as.data.frame(matrix(unlist(strsplit(lines[dataRows], ",")), nrow = length(dataRows), byrow=T))
names(data) <- names
输出:
Type Date Time Duration Type Tag ID Ant Count Gap
1 D 2016-07-05 11:46:24.69 00:00:00.87 HA 900_226000745055 A2 8 1102
2 D 2016-07-05 11:46:43.23 00:00:01.12 HA 900_226000745055 A2 10 143