I have nested tibbles, within a list, within a list, here's the structure:
I basically need to rbind the dataframes that are inside everything. The result would be 6 dataframes in a list, one for each season(winter/summer) and species combination.
> glimpse(list_graphs)
List of 2
$ winter:List of 3
..$ species1: tibble [161 x 1] (S3: tbl_df/tbl/data.frame)
..$ species2: tibble [38 x 1] (S3: tbl_df/tbl/data.frame)
..$ species3: tibble [72 x 1] (S3: tbl_df/tbl/data.frame)
$ summer:List of 3
..$ species1: tibble [33 x 1] (S3: tbl_df/tbl/data.frame)
..$ species2: tibble [2 x 1] (S3: tbl_df/tbl/data.frame)
..$ species3: tibble [52 x 1] (S3: tbl_df/tbl/data.frame)
I've tried:
map(list_graphs, function(x) {
map(x, function(x){
map(x,~do.call(rbind,x))
}
)
})
However, this results in the following which is incorrect:
List of 2
$ winter:List of 3
..$ species1:List of 1
.. ..$ graph_layer:List of 161
.. .. ..- attr(*, "dim")= int [1:2] 1 161
.. .. ..- attr(*, "dimnames")=List of 2
..$ species2:List of 1
.. ..$ graph_layer:List of 38
.. .. ..- attr(*, "dim")= int [1:2] 1 38
.. .. ..- attr(*, "dimnames")=List of 2
..$ species3:List of 1
.. ..$ graph_layer:List of 72
.. .. ..- attr(*, "dim")= int [1:2] 1 72
.. .. ..- attr(*, "dimnames")=List of 2
$ summer:List of 3
..$ species1:List of 1
.. ..$ graph_layer:List of 33
.. .. ..- attr(*, "dim")= int [1:2] 1 33
.. .. ..- attr(*, "dimnames")=List of 2
..$ species2:List of 1
.. ..$ graph_layer:List of 2
.. .. ..- attr(*, "dim")= int [1:2] 1 2
.. .. ..- attr(*, "dimnames")=List of 2
..$ species3:List of 1
.. ..$ graph_layer:List of 52
.. .. ..- attr(*, "dim")= int [1:2] 1 52
.. .. ..- attr(*, "dimnames")=List of 2
I'm sure it's a relatively easy fix, but I just can't work it out. I'm hoping someone can suggest solution based on structure I have above, if not I'll try and get a working regex dataframe.
Thank you
CodePudding user response:
You could use map_dfr
bind_rows
:
library(tidyverse)
map_dfr(list_graphs, ~ bind_rows(.x, .id = "species"), .id = "season")
# # A tibble: 6 × 3
# season species x
# <chr> <chr> <dbl>
# 1 winter species1 1
# 2 winter species2 2
# 3 winter species3 3
# 4 summer species1 4
# 5 summer species2 5
# 6 summer species3 6
Data
list_graphs <- list(winter = list(species1 = tibble(x = 1), species2 = tibble(x = 2), species3 = tibble(x = 3)),
summer = list(species1 = tibble(x = 4), species2 = tibble(x = 5), species3 = tibble(x = 6)))
glimpse(list_graphs)
# List of 2
# $ winter:List of 3
# ..$ species1: tibble [1 × 1] (S3: tbl_df/tbl/data.frame)
# ..$ species2: tibble [1 × 1] (S3: tbl_df/tbl/data.frame)
# ..$ species3: tibble [1 × 1] (S3: tbl_df/tbl/data.frame)
# $ summer:List of 3
# ..$ species1: tibble [1 × 1] (S3: tbl_df/tbl/data.frame)
# ..$ species2: tibble [1 × 1] (S3: tbl_df/tbl/data.frame)
# ..$ species3: tibble [1 × 1] (S3: tbl_df/tbl/data.frame)
CodePudding user response:
Since you don't provide a reproducible example, here's how I understand what you are dealing with:
You have (something like)
l <- list(
winter = list(
species1 = list(tibble(x = 1), tibble(x = 2), tibble(x = 3)),
species2 = list(tibble(x = 4), tibble(x = 5), tibble(x = 6)),
species3 = list(tibble(x = 7), tibble(x = 8), tibble(x = 9))
),
summer = list(
species1 = list(tibble(x = 10), tibble(x = 11), tibble(x = 12)),
species2 = list(tibble(x = 13), tibble(x = 14), tibble(x = 15)),
species3 = list(tibble(x = 16), tibble(x = 17), tibble(x = 18))
)
)
Here's an approach that preserves names and returns a list of (row-bound) tibbles:
map(names(l), function(name) set_names(
map(l[[name]], ~ map_dfr(.x, ~ .x)),
paste0, name
)
) %>%
flatten()
Outcome (of str()
for brevity)
List of 6
$ species1winter: tibble [3 × 1] (S3: tbl_df/tbl/data.frame)
..$ x: num [1:3] 1 2 3
$ species2winter: tibble [3 × 1] (S3: tbl_df/tbl/data.frame)
..$ x: num [1:3] 4 5 6
$ species3winter: tibble [3 × 1] (S3: tbl_df/tbl/data.frame)
..$ x: num [1:3] 7 8 9
$ species1summer: tibble [3 × 1] (S3: tbl_df/tbl/data.frame)
..$ x: num [1:3] 10 11 12
$ species2summer: tibble [3 × 1] (S3: tbl_df/tbl/data.frame)
..$ x: num [1:3] 13 14 15
$ species3summer: tibble [3 × 1] (S3: tbl_df/tbl/data.frame)
..$ x: num [1:3] 16 17 18