获取带有子列表的参数列表

get an argument list with sublists

我想展平这个参数列表

args <- list(
  a = 1,
  b = "2",
  list = list(c = 3, d = list(d1 = 5, d2 = 6)),
  e = data.frame(e1 = c("a", "b"), e2 = c(7, 8))
)

在此

args <- list(
  a = 1,
  b = "2",
  c = 3, 
  d = list(d1 = 5, d2 = 6),
  e = data.frame(e1 = c("a", "b"), e2 = c(7, 8))
)

因为我需要开始工作这个函数调用

g <- function(x, y, ...){
  do.call(f, x, y, ...)
}

g(x = x1, y = y1, args)

那行不通:

reduce(
  .x = args,
  .f = function(x) {
    ifelse(
      is.list(x),
      lapply(x, `[[`),
      x
    )
  }
)

抛出

Error in fn(out, elt, ...) : unused argument (elt)

更新: 到 OP 新数据:

purrr::c(flatten(args[1:3]), args[4])

$a
[1] 1

$b
[1] "2"

$c
[1] 3

$d
$d$d1
[1] 5

$d$d2
[1] 6


$e
  e1 e2
1  a  7
2  b  8

正如您在问题中所说的“我想展平这个参数列表”-> 我们可以使用 purrrs flatten() 函数:

library(purrr)

flatten(args)
$a
[1] 1

$b
[1] "2"

$c
[1] 3

$d
$d$d1
[1] 5

$d$d2
[1] 6


$e
[1] 5

您可以使用 for 循环尝试下面的代码

res <- c()
for (v in args) {
    if (is.list(v) & !is.data.frame(v)) {
        res <- c(res,v)
    } else {
        res <- c(res, list(v))
    }
}

或通过Reduce

res <- Reduce(
    function(x,y) {
        c(x, ifelse(is.list(y) & !is.data.frame(y), I, list)(y))
    },
    args,
    c()
)

你将获得

> res
[[1]]
[1] 1

[[2]]
[1] "2"

$c
[1] 3

$d
$d$d1
[1] 5

$d$d2
[1] 6


[[5]]
  e1 e2
1  a  7
2  b  8

地图的输出总是一样暗淡。所以你需要一个for循环。

output <- NULL
for (x in seq(length(args))) {
   list <- args[x]
  if (is.list(args[[x]]) && !is.data.frame(args[[x]])) {
    list <- flatten(args[x])
  }
  output <- append(output, list)
}
output
$a
[1] 1

$b
[1] "2"

$c
[1] 3

$d
$d$d1
[1] 5

$d$d2
[1] 6


$e
  e1 e2
1  a  7
2  b  8