Unable to use variable file name in readRDS loop - unknown input format error

I am attempting a simple short script whereby I import all RDS files from a certain location. I can get the readRDS to work when hard-coding the file name, but when I attempt to use a variable and Paste to accomplish the same thing, I get an error:

"Error in readRDS(file = paste0("~/R/SFDC_Analysis/Telemetry/Rda/", varFileName, :
unknown input format"

while (n <= varNumFiles)
{

varFileName <- df_listFiles[n, ]
varFileName <- varFileName

df_Import <- readRDS(file = paste0("~/R/SFDC_Analysis/Telemetry/Rda/",varFileName, sep = ""))

n <- n + 1

}

One way: use {here}here() or setwd to the directory with the files. Won't render properly as a reprex

dir() -> a
b <- seq(1:3)
for(i in a){readRDS(a[1]) -> b[i]}
b <- b[-c(1,2,3)]
str(b)

is the file ".rds" or ".rda"? Asking because of the directory name: saveRDS() generates rds files, save() generates rda (or RData) files, and they are read with readRDS() and load() respectively.

The extension is merely a convenience convention: it can be anything. owever, whatever it is, it is case sensitive.

readRDS returns an object that must be captured by assignment, and load assigns the return object to the name of the object read in. readRDS is preferred for a variety of reasons.

1 Like

Yes, agree perfectly (except that on Windows it is not case-sensitive).

I wasn't clear, what I meant is that, if the file was generated with save(), then attempting to use readRDS() on it will give exactly that error. And since the directory containing these files is named Rda, this strongly suggests that it might be the case.

You're right that the extension isn't necessarily informative, these could be Rdata files saved with ".rds" in their name, my answer was confusing. I should have simply said: "try opening them with load() rather than readRDS()".

My bad. Rds is a single, serialized object that can be loaded with either load or readRDS. Rda is a synonym for Rdata, is not serialized and can contain multiple objects, so cannot be read by readRDS.

I suspect the issue here is that readRDS can only handle a single filename at a time, you can't pass a vector of filenames to it.

Try using purrr::map to pass each filename one at a time:

import_rds <- function(file) {
  
  out <- stringr::str_extract(file, "[^/].+(?=\\.Rds$)")
  
  x <- readRDS(here::here(file))
  
  assign(out, x, envir = .GlobalEnv)
  
}


list.files(here::here(), pattern = "\\.Rds$", recursive = TRUE) %>% 
  purrr::map(import_rds)

This should be a simpler solution:

# check this captures your required files
files_to_import <- list.files(path = "R/SFDC_Analysis/Telemetry/Rda", pattern = "*.rds", full.names = TRUE)

df <- purrr::map_dfr(files_to_import, readRDS)

This topic was automatically closed 21 days after the last reply. New replies are no longer allowed.

If you have a query related to it or one of the replies, start a new topic and refer back with a link.