Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Join and rename data frame based on matching columns in another data frame

Tags:

r

Suppose I have something like the IRIS dataset and I want to change the names of the data. I have the names saved in a separate data frame such as:

     old_names    new_names
1 Sepal.Length Sepal_Length
2  Sepal.Width  Sepal_Width
3 Petal.Length Petal_Length
4  Petal.Width  Petal_Width
5      Species      Species

So, I want to replace the iris dataset with the "new_names" data in the data frame by matching the column col_names with the iris data frame column names.

Expected output (but not using sub or similar to get the result:

> names(iris) <- sub("\\.", "_", names(iris))
> iris
    Sepal_Length Sepal_Width Petal_Length Petal_Width    Species
1            5.1         3.5          1.4         0.2     setosa
2            4.9         3.0          1.4         0.2     setosa
3            4.7         3.2          1.3         0.2     setosa
4            4.6         3.1          1.5         0.2     setosa

Question: use some left_join type matching to match the columns up with the dataframe and then rename another data frame based on the matches.

Code and data:

iris

cols = colnames(iris)
data.frame(
  old_names = names(iris),
  new_names = sub("\\.", "_", cols)
)
like image 810
user113156 Avatar asked Oct 31 '25 12:10

user113156


1 Answers

You can rename using a named vector and any_of(). The use of any_of is to avoid errors if your dictionary data contains names that don't exist in the data.

iris %>%
  rename(any_of(tibble::deframe(dict[2:1])))

#     Sepal_Length Sepal_Width Petal_Length Petal_Width    Species
# 1            5.1         3.5          1.4         0.2     setosa
# 2            4.9         3.0          1.4         0.2     setosa
# 3            4.7         3.2          1.3         0.2     setosa

where dict is

dict <- data.frame(
  old_names = names(iris),
  new_names = sub("\\.", "_", cols)
)

An alternative is using rename_with and match:

iris %>%
  rename_with(~ dict$new_names[match(.x, dict$old_names)])
like image 60
Darren Tsai Avatar answered Nov 02 '25 02:11

Darren Tsai



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!