8

I try to rename the column names with the first row of the data.

use first row data as column names in r

use %>% with replacement functions like colnames()<-

The problem that I counter is that doing this process without breaking the dplyr pipeline as I would like to continue doing some other stuff after renaming the columns.

There is comment in this post about rename function dplyr::rename may be more convenient if you are only (re)naming a few out of many columns (it requires writing both the old and the new name; see @Richard Scriven's answer)

However, in my real data the number of columns is not fixed and so I need to use something like to select the columns select(X9:max(ncol(.)))

df <- data.frame(replicate(10,sample(100,2,rep=TRUE)))


  X1 X2 X3 X4 X5 X6 X7 X8 X9 X10
1 77 40 45 98 75 17  5 33 53  94
2 43 67 82 42 63 90 14 65  4  98

library(dplyr)
df1 <- df %>%
  select(X8,X9,X10)%>%
  ....

the expected output after selection and renaming the columns

  33 53  94
1 65  4  98
Alexander
  • 4,527
  • 5
  • 51
  • 98
  • 9
    `df %>% setNames(as.character(df[1,]))` – IceCreamToucan May 30 '18 at 17:59
  • So to clarify, you want to keep only some columns `(X9:end)`, as well as get the names from the first row? – Calum You May 30 '18 at 18:00
  • @Ryan Perfect. Is it possible to remove the first row after setNames ? Because the output right know is still keeping the first row . – Alexander May 30 '18 at 18:02
  • @CalumYou That is correct! – Alexander May 30 '18 at 18:03
  • @Ryan One more thing How can I rename only selected columns after the `select` `df1 <- df %>% select(X8,X9,X10)%>% setNames(as.character(.[1,X9:max(ncol(.))]))` – Alexander May 30 '18 at 18:08
  • You can remove the first row with `df %>% .[-1,]`. If you want to rename specific columns you probably want the `rename` function – IceCreamToucan May 30 '18 at 18:32
  • @Ryan I tried `setNames(2:max(ncol(.)), c(as.character(.[1,])))`. but no luck! You mean `setnames` inside of `rename`? – Alexander May 30 '18 at 18:35
  • rename as in `df %>% rename(newname1 = oldname1, newname2 = oldname2,.....)` – IceCreamToucan May 30 '18 at 18:38
  • @Ryan well that is the hurdle point. My column names across the data is not same and there are at least 50 columns in each data. In my real data I try to load the different files and rename the column names with the first row of selected columns. – Alexander May 30 '18 at 18:40
  • @Ryan Why `setNames(as.character(.[1,X9:max(ncol(.))]))` is not working ? or this `setNames(as.character(.[1,2:max(ncol(.))]))` – Alexander May 30 '18 at 18:41

4 Answers4

1

You can easily do it by naming columns as first row and then remove the first row.

library(dplyr)
df <- df %>%
  select(X8,X9,X10)

names(df) <- df[1,]
df <- df[-1,]

Macosso
  • 1,352
  • 5
  • 22
1

You could do something like this

library(tidyverse)
df <- data.frame(replicate(10,sample(100,2,rep=TRUE)))
df
#>   X1 X2 X3 X4 X5 X6 X7 X8 X9 X10
#> 1 22 64 23 11 36 46 87 57 90  96
#> 2 62 46 15  9 77 84 70 32 71   8

cols_2_select <- c('X8','X9','X10')

df %>%
  select(all_of(cols_2_select)) %>% 
  set_names(df %>% select(all_of(cols_2_select)) %>% slice(1) %>% as.character()) %>% 
  slice(-1)
#>   57 90 96
#> 1 32 71  8

Created on 2021-04-16 by the reprex package (v1.0.0)

cropgen
  • 1,920
  • 15
  • 24
0
set.seed(502)
df <- data.frame(replicate(10, sample(100, 2, rep=TRUE)))

> df
  X1 X2 X3 X4 X5 X6 X7 X8 X9 X10
1 79  6 82 23 36 58 95 30 60  42
2 89 77  9 13 79 97  1 10 48  66

In base R we can do

df1 <- "colnames<-"(df[2 , x <- paste0("X", 8:10)], df[1, x])

> df1
  30 60 42
2 10 48 66
jay.sf
  • 60,139
  • 8
  • 53
  • 110
0

Since I don't see this here and it seems to be simpler/more tidyverse-ish than other options: set_names(slice(.,1)) (to name by the first row; explicit coercion to character isn't necessary) followed by slice(-1) (to discard the first row since you don't need it any more) ...

library(tidyverse)
df1 <- (df 
    %>% select(X8:X10) 
    %>% set_names(slice(.,1)) 
    %>% slice(-1)
)

(set_names taken from @cropgen's answer)

Ben Bolker
  • 211,554
  • 25
  • 370
  • 453