2

I have a data frame which looks like this

value <- c(1:1000)
group <- c(1:5)
df <- data.frame(value,group)

And I want to use this function on my data frame

myfun <- function(){
  wz1 <- df[sample(nrow(df), size = 300, replace = FALSE),]
  wz2 <- df[sample(nrow(df), size = 10, replace = FALSE),]
  wz3 <- df[sample(nrow(df), size = 100, replace = FALSE),]
  wz4 <- df[sample(nrow(df), size = 40, replace = FALSE),]
  wz5 <- df[sample(nrow(df), size = 50, replace = FALSE),]

  wza <- rbind(wz1,wz2, wz3, wz4, wz5)
  wza_sum <- aggregate(wza, by = list(group_ID=wza$group), FUN = sum)
  return(list(wza = wza,wza_sum = wza_sum))
}

Right now I am returning one list which includes wza and wza_sum.

Is there a way to return two separate list in which one contains wza and the other list contains wza_sum?

The aggregate() function needs to be in myfun() because I want to replicate myfun() 100 times using

dfx <- replicate(100,myfun(),simplify = FALSE,)
C. Toni
  • 133
  • 7
  • 2
    I might be missing something, but if you do return(list(wza = list(wza),wza_sum = list(wza_sum))) ; this gives you two list? – StupidWolf Dec 14 '19 at 20:45
  • 2
    It is simple to split the list into parts after you run the function. The function cannot return more than one object as you may have discovered if you tried `return(wza, wza_sum)`. You can often get around limitations like this, but the side effects can be difficult to diagnose when something goes wrong. For instance the function could save objects in the environment that you could access later. – dcarlson Dec 14 '19 at 20:45
  • 1
    Or do it like this after your replicate, list1 = sapply(dfx,"[[","wza_sum"); list2 = lapply(dfx,"[[","wza") – StupidWolf Dec 14 '19 at 20:48

1 Answers1

0

A function should take one input (or set of inputs), and return only one output (or a set of outputs). Consider the simple example of

myfunction <- function(x) {
  x
  x ** 2
}

Unless you are calling return() early (which you usually don't), the last object is returned. In fact, if you try to return two objects, e.g. return(1,2) you are met with

Error in return(1, 2) : multi-argument returns are not permitted

That is why the solution proposed by @StupidWolf in the comments is the most appropriate one, where you use return(list(wza = list(wza),wza_sum = list(wza_sum))). You then have to perform the necessary post-processing of splitting the lists if appropriate.

mhovd
  • 3,724
  • 2
  • 21
  • 47