Tho*_*del 2 loops r web-scraping rvest
我需要从 URL 下载一系列 Excel 文件,所有文件如下所示:
\nhttp://example.com/orResultsED.cfm?MODE=exED&ED=01&EventId=31\nhttp://example.com/orResultsED.cfm?MODE=exED&ED=02&EventId=31\n...\nhttp://example.com/orResultsED.cfm?MODE=exED&ED=87&EventId=31\n
Run Code Online (Sandbox Code Playgroud)\n\xc2\xa0
\n我在循环内有一些构建块,例如:
\nfor(i in 1:87) {\n url <- paste0("http://example.com/orResultsED.cfm?MODE=exED&ED=", i, "&EventId=31")\n file <- paste0("Data/myExcel_", i, ".xlsx")\n if (!file.exists(file)) download.file(url, file) \n}\n
Run Code Online (Sandbox Code Playgroud)\n\xc2\xa0
\n我的问题:
\nseq
前面加上 0 (我尝试过sprintf
但没有运气)\xc2\xa0
\n@akrun 解决方案效果很好。但事实证明,并非所有 Excel 文件都具有相同的列数:
\nmap(files, ~read.xlsx(.x, \n colNames = FALSE,\n sheet = 1, \n startRow = 4,\n )) %>%\n bind_rows\n\nError in bind_rows_(x, .id) : \n Column `X1` can't be converted from numeric to character\n
Run Code Online (Sandbox Code Playgroud)\n我认为这个错误实际上指向列数不相等。我尝试添加fill = NA
(测试时map_df()
),但没有帮助。
我们可以用以下方法创建它sprintf
paste0("http://example.com/orResultsED.cfm?MODE=exED&ED=", sprintf("%02d", 1), "&EventId=31")
#[1] "http://example.com/orResultsED.cfm?MODE=exED&ED=01&EventId=31"
Run Code Online (Sandbox Code Playgroud)
在循环,
for(i in 1:87) {
i1 <- sprintf('%02d', i)
url <- paste0("http://example.com/orResultsED.cfm?MODE=exED&ED=", i1, "&EventId=31")
file <- paste0("Data/myExcel_", i, ".xlsx")
if (!file.exists(file)) download.file(url, file)
}
Run Code Online (Sandbox Code Playgroud)
假设文件下载到工作目录中
files <- list.files(full.names = TRUE)
library(openxlsx)
library(purrr)
library(dplyr)
map(files, ~read.xlsx(.x, sheet = 1, startRow = 3)) %>%
bind_rows
Run Code Online (Sandbox Code Playgroud)
或者正如评论中提到的@hrbrmstr,map_df
可以使用它返回单个数据集
map_df(files, ~read.xlsx(.x, sheet = 1, startRow = 3))
Run Code Online (Sandbox Code Playgroud)
根据OP的评论,某些数据集的列类似乎存在差异。在这种情况下,bind_rows
会出现错误。一种选择是使用rbindlist
fromdata.table
map(files, ~read.xlsx(.x, sheet = 1, startRow = 3)) %>%
data.table::rbindlist(fill = TRUE)
Run Code Online (Sandbox Code Playgroud)