r syntax

¿Existe una función base R para ordenar dinámicamente columnas data.frame similares a dplyr everything()?



syntax (3)

Supongamos que tiene un data.frame y desea reordenar dinámicamente las columnas utilizando la base R. Los datos de entrada siempre se verán así. Siempre contendrá las variables id, mes y año, así como un número variable de variables de datos (denotadas como v1, v2, v3, etc.)

df1 <- data.frame( id = 1:5, v1 = LETTERS[1:5], v2 = rep(2,5), v3 = rep(10,5), month = c("jan", "jan", "mar", "oct", "dec"), year = c(1999, 2001, 1984, 1979, 2019), stringsAsFactors = F)

Me gustaría reordenar las columnas de modo que id, mes y año sean siempre las primeras tres columnas, y luego coloque las variables de datos que comienzan en la columna 4.

df2 <- data.frame( id = 1:5, month = c("jan", "jan", "mar", "oct", "dec"), year = c(1999, 2001, 1984, 1979, 2019), v1 = LETTERS[1:5], v2 = rep(2,5), v3 = rep(10,5), stringsAsFactors = F)

Soy consciente de que esto se puede hacer con dplyr :: select junto con dplyr :: everything.

library(dplyr) df2 <- df1 %>% select(id, month, year, everything())

Pero me gustaría lograr el mismo resultado utilizando la base R.

Lo mejor que se me ocurrió es,

keep1 <- c("id", "month", "year") keep2 <- names(df1)[!names(df1) %in% keep1] keep3 <- c(keep1, keep2) df2 <- df1[, keep3]

¿Podría haber una solución más elegante? ¿Podría haber una función en la base R similar a dplyr :: everything?


Otra opción

df1[, unique(c(which(names(df1) %in% keep1), seq_along(df1)))]

o

df1[, unique(c("id", "month", "year", names(df1)))]


Puedes usar setdiff :

df1[, c(keep1, setdiff(names(df1), keep1))]


df1[order(match(names(df1), keep1, nomatch = NCOL(df1) + 1))] # id month year v1 v2 v3 #1 1 jan 1999 A 2 10 #2 2 jan 2001 B 2 10 #3 3 mar 1984 C 2 10 #4 4 oct 1979 D 2 10 #5 5 dec 2019 E 2 10