【问题标题】:Extract a vector from nested lists in R从 R 中的嵌套列表中提取向量
【发布时间】:2021-09-07 19:51:45
【问题描述】:

我正在尝试根据同一个嵌套列表中另一个变量\元素的值从嵌套列表中提取一个向量。希望我的例子能解释我想要做什么。

首先,我有一个这样的列表:

## Create the inner lists
# Inner list 1
listInner1 <- list(
  value = c(0.25),
  index = c(1, 2, 3, 4, 5, 6, 7, 8, 9, 10),
  left  = c(),
  right = c()
)

listInner1$left$index  <- c(1, 2, 3, 4, 5)
listInner1$left$good   <- TRUE
listInner1$right$index <- c(6, 7, 8, 8, 10)
listInner1$right$good  <- TRUE

# Inner list 2
listInner2 <- list(
  value = c(1.5),
  index = c(1, 2, 3, 4, 5, 6, 7, 8, 9, 10),
  left  = c(),
  right = c()
)

listInner2$left$index  <- c(1, 2, 3)
listInner2$left$good   <- TRUE
listInner2$right$index <- c(4, 5, 6, 7, 8, 9, 10)
listInner2$right$good  <- TRUE

# Inner list 3
listInner3 <- list(
  value = c(0.5),
  index = c(1, 2, 3, 4, 5, 6, 7, 8, 9, 10),
  left  = c(),
  right = c()
)

listInner3$left$index  <- c(1, 2, 3, 4, 5)
listInner3$right$index <- c( 6, 7, 8, 9, 10)
listInner3$left$left$index  <- c(2, 4, 6, 8, 10)
listInner3$left$right$index <- c(1, 3, 5 ,7, 9)
listInner3$left$left$good <- TRUE
listInner3$left$right$good <- TRUE


# put all inner lists into single list object
listMiddle <- list(listInner1, listInner2, listInner3)

# one more list for fun
listMaster <- list(listMiddle)

如您所见,嵌套列表的某些leftright 元素包含元素good = TRUE,而有些则不包含。

我想要做的是如果一个特定的嵌套列表包含元素 good = TRUE 然后从同一个嵌套列表中提取元素 index

例如,为上述示例手动创建我想要的输出将如下所示:

ans <- list(
  index.1 = c(1, 2, 3, 4, 5),
  index.2 = c(6, 7, 8, 8, 10),
  index.3 = c(1, 2, 3),
  index.4 = c(4, 5, 6, 7, 8, 9, 10),
  index.5 = c(2, 4, 6, 8, 10),
  index.6 = c(1, 3, 5 ,7, 9)
)

对象ans 包含所有index 向量,这些向量包含在还包含good = TRUE 的嵌套列表中。

关于如何做到这一点的任何建议?

【问题讨论】:

    标签: r


    【解决方案1】:

    这是一个选项,我们使用rrapply 将嵌套元素bind 转换为更容易接近的格式,然后,我们获得“好”列的索引,从该位置索引中提取相应的“索引”元素在map2(基于TRUE 值)、transposelistkeep 中循环仅大于 0 的元素 lengthflattenlist 并设置名称(如果需要)

    library(purrr)
    library(rrapply)
    library(stringr)
    library(dplyr)
    out <- rrapply(listMaster, how = 'bind')
    i1 <- grep('good', names(out))
    map2(out[i1-1], out[i1], `[`) %>%
       transpose %>%
       map( ~ keep(.x, lengths(.x) > 0)) %>%
       flatten %>%
       setNames(str_c('index.', seq_along(.)))
    

    -输出

    $index.1
    [1] 1 2 3 4 5
    
    $index.2
    [1]  6  7  8  8 10
    
    $index.3
    [1] 1 2 3
    
    $index.4
    [1]  4  5  6  7  8  9 10
    
    $index.5
    [1]  2  4  6  8 10
    
    $index.6
    [1] 1 3 5 7 9
    

    【讨论】:

    • 非常复杂的问题。你是如何在你的大脑中得到这一切的? :-)
    • @TarJae 我认为仅基于我的功能它看起来很复杂。可能,它可能更容易完成,即在 rrapply 本身内。我没有尝试太多,但我希望它更容易
    • 完美运行。我尝试了好几个小时,无法绕开它。谢谢
    • @TarJae 请不要相信我一口气就做到了。不,我没有。只是当我尝试某些东西时,我确实尝试了几种方法,即查找函数中是否存在任何漏洞。其中一些可能不在文档中。我通过反复试验发现了一些。我认为最好的学习方法是尝试一些东西,当你发现错误时,你会学到关于该功能非常独特的东西
    • @akrun,很高兴听到。所以我这样做并没有错!虽然最后你是对的非常耗时!高手请看这里stackoverflow.com/questions/69093216/…>这个答案你怎么看?
    猜你喜欢
    • 2021-12-29
    • 2021-03-06
    • 1970-01-01
    • 2017-12-31
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-09-21
    相关资源
    最近更新 更多