3

I want to change few specific column names of a data frame using dplyr's pipe. Below is one such example -

library(dplyr)
head(mtcars)

Now let say, I want to change 2nd and 3rd column names to "a" and "b" respectively. Trivially, I could do it as

colnames(mtcars)[2] <- "a"
colnames(mtcars)[3] <- "b"

However I want to do it using pipe and in a single line to enhance readability.

Any suggestion how should I do it?

Many thanks for your time.

Brian Smith
  • 1,200
  • 4
  • 16

3 Answers3

6

With tidyverse, we can use rename_with

library(dplyr)
mtcars <- mtcars %>%
       rename_with(~ c('a', 'b'), 2:3)

names(mtcars)
#[1] "mpg"  "a"    "b"    "hp"   "drat" "wt"   "qsec" "vs"   "am"   "gear" "carb"

We could use replace with names<-

head(mtcars) %>% 
     `names<-`(replace(names(.), 2:3, c('a', 'b')))

-output

#                   mpg a   b  hp drat    wt  qsec vs am gear carb
#Mazda RX4         21.0 6 160 110 3.90 2.620 16.46  0  1    4    4
#Mazda RX4 Wag     21.0 6 160 110 3.90 2.875 17.02  0  1    4    4
#Datsun 710        22.8 4 108  93 3.85 2.320 18.61  1  1    4    1
#Hornet 4 Drive    21.4 6 258 110 3.08 3.215 19.44  1  0    3    1
#Hornet Sportabout 18.7 8 360 175 3.15 3.440 17.02  0  0    3    2
#Valiant           18.1 6 225 105 2.76 3.460 20.22  1  0    3    1
akrun
  • 874,273
  • 37
  • 540
  • 662
  • Thanks. That works. However is there any way I can do this using assignment function ` '[<-'() `? – Brian Smith May 07 '21 at 19:57
  • 1
    @BrianSmith Your post says `in a single line to enhance readability.`. I am not sure how that enhances readability – akrun May 07 '21 at 19:58
  • I am just asking out of curiosity. – Brian Smith May 07 '21 at 19:59
  • I also noticed that, above approach will work only if all the colnames are unique. For example this code will generate error `%>% rename_with(~ c('a', 'a'), 2:3)`. Is there any way to eliminate this constraint? – Brian Smith May 07 '21 at 20:06
  • @BrianSmith it generates error because that is not a permitted behavior in data.frame. it is not recommended to even assign dupe names in a data.frame though in matrix it is permitted (but I would avoid doing that) – akrun May 07 '21 at 20:08
  • I see. But my data set is fetched from some official source and that has multiple columns with same value. I should not change the column names of that original dataset to make them unique. So I need to find a way to change some column-names even if original data has some duplicity. – Brian Smith May 07 '21 at 20:11
  • @BrianSmith even if you are able to change it to duplicate names, in some subsequent transformation, the `make.unique` will replace it with a unique name – akrun May 07 '21 at 20:11
  • @BrianSmith I added one option with `names<-` – akrun May 07 '21 at 20:12
4

If you don't mind using data.table, then here is another option besides dplyr

setnames(as.data.table(mtcars), 2:3, c("a", "b"))[]
ThomasIsCoding
  • 96,636
  • 9
  • 24
  • 81
1

We could simply use select:

library(dplyr)
mtcars1 <- mtcars %>%
  select(1, a=2, b=3, everything())

Output:

> colnames(mtcars)
 [1] "mpg"  "cyl"  "disp" "hp"   "drat" "wt"   "qsec" "vs"   "am"   "gear" "carb"
> colnames(mtcars1)
 [1] "mpg"  "a"    "b"    "hp"   "drat" "wt"   "qsec" "vs"   "am"   "gear" "carb"
TarJae
  • 72,363
  • 6
  • 19
  • 66