代码之家  ›  专栏  ›  技术社区  ›  Denis

向列表添加位置索引

  •  0
  • Denis  · 技术社区  · 6 年前

    我想在列表中添加一个顺序元素。假设我有以下清单

    lst <- list("A"=list(e1="a",e2="!"), "B"=list(e1="b", e2="@"))
    $A
    $A$e1
    [1] "a"
    
    $A$e2
    [1] "!"
    
    $B
    $B$e1
    [1] "b"
    
    $B$e2
    [1] "@"
    

    我想附加一个 e3 这是该元素在列表中的位置索引,所以本质上我希望我的列表是:

    $A
    $A$e1
    [1] "a"
    
    $A$e2
    [1] "!"
    
    $A$e3
    [1] 1
    
    $B
    $B$e1
    [1] "b"
    
    $B$e2
    [1] "@"
    
    $B$e3
    [1] 2
    
    0 回复  |  直到 6 年前
        1
  •  1
  •   akrun    6 年前

    我们可以使用 for 循环也

    for(i in seq_along(lst)) lst[[i]]$e3 <- i
    
        2
  •  2
  •   d.b    6 年前
    setNames(lapply(seq_along(lst), function(i){
        temp = lst[[i]]
        temp$e3 = i
        temp
    }), names(lst))
    #$`A`
    #$`A`$`e1`
    #[1] "a"
    
    #$`A`$e2
    #[1] "!"
    
    #$`A`$e3
    #[1] 1
    
    
    #$B
    #$B$`e1`
    #[1] "b"
    
    #$B$e2
    #[1] "@"
    
    #$B$e3
    #[1] 2
    
        3
  •  2
  •   dipetkov    6 年前

    这里有一个解决方案,它不假设子列表具有相同数量的已知元素。

    library("tidyverse")
    library("glue")
    
    lst <- list("A"=list(e1="a",e2="!"), "B"=list(e1="b", e2="@"))
    
    # The part
    # `setNames(list(.y), glue("e{length(.x) + 1}"))`
    # creates a one-element list named accordingly to append to the previous list
    map2(lst, seq(lst),
         ~ append(.x, setNames(list(.y), glue("e{length(.x) + 1}") )))
    #> $A
    #> $A$e1
    #> [1] "a"
    #> 
    #> $A$e2
    #> [1] "!"
    #> 
    #> $A$e3
    #> [1] 1
    #> 
    #> 
    #> $B
    #> $B$e1
    #> [1] "b"
    #> 
    #> $B$e2
    #> [1] "@"
    #> 
    #> $B$e3
    #> [1] 2
    
    # If naming the additional element is not important, then this can simplified to
    map2(lst, seq(lst), append)
    # or
    map2(lst, seq(lst), c)
    

    于2019-03-06由 reprex package (v0.2.1)

        4
  •  2
  •   markus    6 年前

    使用另一个选项 Map

    Map(function(x, y) c(x, "e3" = y), x = lst, y = seq_along(lst))
    #$A
    #$A$e1
    #[1] "a"
    
    #$A$e2
    #[1] "!"
    
    #$A$e3
    #[1] 1
    
    
    #$B
    #$B$e1
    #[1] "b"
    
    #$B$e2
    #[1] "@"
    
    #$B$e3
    #[1] 2
    

    这可以写得更简洁

    Map(c, lst, e3 = seq_along(lst))
    

    感谢@thelatemail

        5
  •  1
  •   Michael Scott    6 年前

    假设我理解正确,您希望向每个嵌套列表添加第三个元素,该列表包含其父列表中该列表的索引。这工作:

    library(rlist)    
    lst <- list("A"=list(e1="a",e2="!"), "B"=list(e1="b", e2="@"))
    for(i in seq(1:length(lst))){
      lst[[i]] <- list.append(lst[[i]],e3=i)  
    }
    lst
    
        6
  •  1
  •   divibisan    6 年前

    我们可以沿着 lst 具有 lapply ,将此顺序索引添加到每个元素。

    lst2 <- lapply(seq_along(lst), function(i) {
        df <- lst[[i]]
        df$e3 <- i
        return(df)
    })
    names(lst2) <- names(lst) # Preserve names from lst
    

    或者,如果您不害怕修改到位:

    lapply(seq_along(lst), function(i) {
        lst[[i]]$e3 <<- i
    })
    

    两者输出相同:

    $A
    $A$e1
    [1] "a"
    $A$e2
    [1] "!"
    $A$e3
    [1] 1
    
    
    $B
    $B$e1
    [1] "b"
    $B$e2
    [1] "@"
    $B$e3
    [1] 2