Can purrr map recursively? How to get every name, value, and attribute from a nested list?

I have this list:

l <- list(
  a = list(v1 = "value1",
           v2 = "value2"),
  b = "something",
  c = list(v1 = "value3",
           v2 = "value4",
           v3 = list(
             t1 = "value5",
             t2 = "value5")
           )
)
attr(l$b, "a1") <- "att1"
attr(l$c, "a1") <- "att2"

I want to: (1) print every name in the list; (2) print every value in the list; and (3) print every attribute in the list. It would be great if I could do: map(l, names, recursive = TRUE), a la the recursive option in list.files and dir. But that's not possible, as far as I can tell.

Hey @daranzolin! This recent thread covered a similar topic, so it might help you with this :slightly_smiling_face:

1 Like

@rensa thanks, I did not know about rapply! It's alllmmoosttt the solution:

# Gets all names
> names(rapply(l, function(x) x))
[1] "a.v1"    "a.v2"    "b"       "c.v1"    "c.v2"    "c.v3.t1" "c.v3.t2"

# Gets all values
> rapply(l, function(x) x)
       a.v1        a.v2           b        c.v1        c.v2     c.v3.t1     c.v3.t2 
   "value1"    "value2" "something"    "value3"    "value4"    "value5"    "value5" 

# Does NOT get all attributes, missing "att2" from "c"
> rapply(l, attributes)
  b.a1 
"att1" 

Strange that the recursion does not cycle through every part of the object.

I didn't know about rapply either... I would have used unlist:


unlist(l)
#>        a.v1        a.v2           b        c.v1        c.v2     c.v3.t1 
#>    "value1"    "value2" "something"    "value3"    "value4"    "value5" 
#>     c.v3.t2 
#>    "value5"

which gives the same answer as your rapply example. I know this isn't a solution, but rather a bread crumb towards possible solutions.

1 Like

This topic was automatically closed 21 days after the last reply. New replies are no longer allowed.