rjss
rjss

Reputation: 1013

Rename dataframes in a list using a key

I have a list of dataframe and many of the columns will need to be renamed. It will be optimal to setup a key that I can use to rename the dataframe. The variables in the dataframe may or may not exist. I have been looking if there is a function that already do this but have not been able to find anything. The following example shows what I am trying to do.

# This is a dummy list with dataframes that may contain common variables
data_list <- list(
  dfx1 <- mtcars,
  dfx2 <- mtcars %>% rename(`mpg.1` = mpg, `cyl2` = cyl),
  dfx3 <- mtcars %>% rename(`mpg.11` = mpg),
  dfx4 <- mtcars %>% select(-mpg)
)

# Setup a key; the key does not have to be in this format
mykey <- c(
  mpg = c("mpg.1", "mpg.11"),
  cyl = c("cyl2")
)

# Is there a function that I can use to rename based in this key
lapply(x, fun, mykey)

Upvotes: 0

Views: 70

Answers (3)

rjss
rjss

Reputation: 1013

The answer from wimpel works better for my case.

However, the key will need to be defined as a list instead of the definition in the original post.

mykey <- list(
  mpg = c("mpg.1", "mpg.11"),
  cyl = c("cyl2")
)

It can be easily implemented in function (something like):

rename_dfx <- function(dfx, key) {
  length_of_old <- lapply(key, length)
  newvars <- names(key)
  old_vars <- unlist(key)
  new_vars <- rep(newvars, times = unlist(length_of_old))
  
  setnames(dfx, old = old_vars, new = new_vars, skip_absent = TRUE)
  
  dfx
  
}

rename_dfx(data_list[[1]], mykey)
rename_dfx(data_list[[2]], mykey)
lapply(data_list, rename_dfx, key = mykey)

Upvotes: 1

akrun
akrun

Reputation: 886938

We could use map to loop over the list, subset the 'mykey' with the intersecting column names from the list element ('nm1') If the length of 'mykey' is greater than 0, then rename the columns with rename_at

library(dplyr)
library(purrr)
data_list2 <- map(data_list, ~ {
        i1 <- mykey %in% names(.x)
        nm1 <- mykey[i1]
        if(length(nm1) >0) .x %>% 
                 rename_at(vars(nm1), ~ names(nm1)) else .x
 })

Upvotes: 1

Wimpel
Wimpel

Reputation: 27732

Do you mean something like this?

library( data.table )
#sample data
dt1 <- data.table( x = 1, yy = 2 )
dt2 <- data.table( xx = 1, yy = 2 )
L <- list(dt1, dt2)

#actual code renaming columns from old >> new
lapply( L, function(x) setnames( x, old = c("xx", "yy"), new = c("x", "y"), skip_absent = TRUE ) )
 
# [[1]]
#    x y
# 1: 1 2
# 
# [[2]]
#    x y
# 1: 1 2

Upvotes: 1

Related Questions