Reputation: 1249
Just for example, I have a dataframe with columns: name
, n
, mean
and sd
. How do I extract and then save the elements of a list into a single rda
file. The file should contain the generated datasets and not the list.
random.r <- function(df, filename) {
save.random <- function(name, n, mean, sd) {
rn <- rnorm(n=n, mean=mean, sd=sd)
assign(deparse(name), rn)
}
rlist <- sapply(1:nrow(df), function(x)
save.random(df$name[x], df$n[x],df$mean[x],df$sd[x],simplify = FALSE))
save(list = rlist, file = paste(filename,".Rda",sep=""), envir = .GlobalEnv)
}
Cheers
Upvotes: 1
Views: 1880
Reputation: 27408
The trick is to tell R where to find the objects referred to in save
. To do this, provide the list itself as an environment:
save(list=names(rlist), file=..., envir=as.environment(rlist))
Note also that list
must be a vector of object names, so this should be names(rlist)
, not simply rlist
, since the latter is a list of numeric vectors.
The following is a modification of your random.r
, which works as you had intended. At the end of this post I also provide simplified code that achieves the same.
random.r <- function(df, filename) {
save.random <- function(name, n, mean, sd) {
rnorm(n=n, mean=mean, sd=sd)
}
rlist <- setNames(lapply(1:nrow(df), function(x) {
save.random(df$name[x], df$n[x], df$mean[x], df$sd[x])
}), df$name)
save(list = names(rlist), file = paste0(filename, ".rda"),
envir = as.environment(rlist))
}
The key changes above are the specification of names(rlist)
as the list (vector) of element names that you want to save, and as.environment(rlist)
as the environment in which you want R to search for objects with those names. Note also that I've used setNames
to correctly assign elements of df$name
as the names of the resulting elements of rlist
.
A simplified version would be:
rlist <- setNames(mapply(rnorm, d$n, d$mean, d$sd), d$name)
save(list=names(rlist), file='~/../Desktop/foo.rda',
envir=as.environment(rlist))
where d
is your data.frame
. Here, mapply
is a handy shortcut; it steps through the vectors d$n
, d$mean
and d$sd
simultaneously, performing rnorm
each time.
The simplified code can of course be wrapped into a function if you require, e.g.:
f <- function(x, filename) {
rlist <- setNames(mapply(rnorm, x$n, x$mean, x$sd), x$name)
save(list=names(rlist), file=paste0(filename, '.rda'),
envir=as.environment(rlist))
}
d <- data.frame(name=LETTERS, n=sample(100, 26), mean=runif(26), sd=runif(26),
stringsAsFactors=FALSE)
f(d, '~/../Desktop/foo')
Upvotes: 3