如何让mapply函数返回一个列表?

22

假设我有一个创建数据框的函数。我想使用不同的输入值运行该函数,然后将结果合并成一个大的数据框,如下所示:

CreateDataFrame <- function(type="A", n=10, n.true=8) {
  data.frame(success=c(rep(TRUE, n.true), rep(FALSE, n - n.true)), type=type)
}
df <- do.call(rbind, lapply(toupper(letters[1:5]), CreateDataFrame))

我的CreateDataFrame函数有三个参数。在上面的例子中,第二个和第三个参数是固定的。我想做与上面相同的事情,但希望在每次调用时更改第二个和第三个参数。我认为我必须使用mapply,像这样:

mapply("CreateDataFrame", type=toupper(letters[1:5]), n=10, n.true=8:4)

我遇到了问题,因为mapply没有返回列表,这使我无法运行 do.call(rbind, mapply(...))。我该如何得到一个单一的数据框,就像在顶部的例子中一样?

看起来mapply返回了一个列表的矩阵。我原本期望它返回一个数据帧的列表。我应该怎么做才能不同呢?

2个回答

38

如果要返回一个数据框的列表,请将mapply函数的SIMPLIFY参数设置为FALSE。(该参数的默认值为TRUE,这会尝试将结果减少为向量、矩阵或更高维度的数组——这正是你遇到的问题)。

res <- mapply("CreateDataFrame", type=toupper(letters[1:5]), n=10, n.true=8:4, 
              SIMPLIFY = FALSE)

identical(class(res), "list")
[1] TRUE

2
谢谢!回想起来,我应该更仔细地阅读手册。 - Adrian
3
没问题。在我学会这个之前,花费了相当长的一段时间。每当我发现自己在想“如果函数X能做Y就好了”,我就知道函数的创作者很可能已经先我一步想到了这个点子! - Josh O'Brien
10
简化函数需要大写太愚蠢了。它的格式与sapply组函数不匹配。 - adam

5

你可以使用Map函数。它基本上是将mapply的SIMPLIFY设置为FALSE。

Map("CreateDataFrame", type=toupper(letters[1:5]), n=10, n.true=8:4)

哇,这个不错。每天都能学到新东西。 - theforestecologist
2
我不知道!所以我查了一下代码,你说得太对了。> Map function(f,...) {      f <- match.fun(f)      mapply(FUN = f,...,SIMPLIFY = FALSE) } - Drumy

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接