Search code examples
rlistpurrrnames

Recover list names after applying purrr reduce r


Is there a way to keep from losing the name attributes of a list after using purrr::reduce?

Example

I have a list:

library(tidyverse)
l <- list(A = data_frame(ID = c(101, 102, 103),
                         x = c(1,2,3)),
          B = data_frame(ID = c(101, 102, 103),
                         x = c(4,5,6)),
          C = data_frame(ID = c(101, 102, 103),
                         x = c(7,8,9)))

I can join the lists on "ID" using reduce and then use setNames to name the columns like this.

l %>% 
  purrr::reduce(left_join, by = "ID") %>% 
  setNames(c("ID", names(l)))

But I would like to take this list and directly pipe it into purrr::reduce and then rename the columns "A", "B" and "C" without creating object l, but when I do this the list names are no longer available.

Question

What can I do to the code below to change the names of the column "x" without having to create the list l or specify the individual column names?

list(A = data_frame(ID = c(101, 102, 103),
                    x = c(1,2,3)),
     B = data_frame(ID = c(101, 102, 103),
                    x = c(4,5,6)),
     C = data_frame(ID = c(101, 102, 103),
                    x = c(7,8,9))) %>% 
  purrr::reduce(left_join, by = "ID")

Solution

  • You could use imap and set_names from purrr to rename the columns before you merge

    library(purrr)
    list(A = data_frame(ID = c(101, 102, 103),
                        x = c(1,2,3)),
         B = data_frame(ID = c(101, 102, 103),
                        x = c(4,5,6)),
         C = data_frame(ID = c(101, 102, 103),
                        x = c(7,8,9))) %>% 
      imap(.x = ., ~ set_names(.x, c("ID", .y))) %>% 
      reduce(dplyr::left_join, by = "ID")
    # A tibble: 3 x 4
    #     ID     A     B     C
    #  <dbl> <dbl> <dbl> <dbl>
    #1   101     1     4     7
    #2   102     2     5     8
    #3   103     3     6     9