#r #dataframe #rename
Вопрос:
Я пытаюсь переименовать столбцы фрейма данных через таблицу соответствия, фрейм данных с двумя столбцами (имя до и имя после).
В моей ситуации в фрейме данных для переименования могут быть столбцы, на которые нет ссылок в моей таблице соответствия (это не проблема, они не будут переименованы), и, наоборот, таблица соответствия может содержать имена, не включенные в мой фрейм данных. Этот список может быть использован для других кадров данных.
И, по крайней мере, порядок имен может быть разным в 2 кадрах данных, это было бы слишком просто.
У меня есть решение с циклом, но попробуйте найти другое решение, без цикла.
Есть идеи ? Заранее спасибо.
Вот мой код
df_to_rename <- data.frame(annee = 2010:2012,
code_commune = 67000:67002,
duree_occup_ou_vacance_tranche = 1:3,
nb_total_logements = 100:102,
secret_not_in_list = 1:3)
liste_noms_col <- data.frame(noms_origine = c("mode_occ",
"code_commune",
"annee",
"duree_occup_ou_vacance_tranche",
"nb_total_logements"),
noms_nouveaux = c("mode d'occupation - not included",
"code INSEE commune",
"Année",
"durée d'occupation (ou vacance)",
"Nombre de logements"))
##### Rename by loop
l_noms <- df_to_rename %>% names()
# (i_nom <- l_noms[1])
for(i_nom in l_noms) {
nom_a_changer <-
liste_noms_col[liste_noms_col$noms_origine == i_nom, "noms_nouveaux"]
# message(i_nom," -> ",nom_a_changer)
if(length(nom_a_changer)>0) {
df_to_rename <- df_to_rename %>%
rename({{nom_a_changer}} := {{i_nom}})
message(i_nom," -> ",nom_a_changer)
}
}
df_to_rename %>% names()
Ответ №1:
Превратитесь liste_noms_col
в список с deframe
, отфильтруйте интересующие имена и rename()
:
library(dplyr)
liste_noms_col <- deframe(liste_noms_col[, 2:1])
liste_noms_col <- liste_noms_col[liste_noms_col %in% names(df_to_rename)]
rename(df_to_rename, !!! liste_noms_col)
Проверка замены triple-bang ( !!!
) «без кавычек» :
expr(
rename(df_to_rename, !!! liste_noms_col)
)
#> rename(df_to_rename, `code INSEE commune` = "code_commune",
#> Année = "annee", `durée d'occupation (ou vacance)` = "duree_occup_ou_vacance_tranche",
#> `Nombre de logements` = "nb_total_logements")
Ответ №2:
Используйте match
и получите новые имена столбцов фрейма данных, в котором он присутствует liste_noms_col
. Для имен столбцов , в которых их нет liste_noms_col
, сохраните исходные столбцы в том виде, в каком они есть.
cols <- liste_noms_col$noms_nouveaux[match(names(df_to_rename), liste_noms_col$noms_origine)]
cols[is.na(cols)] <- names(df_to_rename)[is.na(cols)]
names(df_to_rename) <- cols
df_to_rename
# Année code INSEE commune durée d'occupation (ou vacance) Nombre de logements secret_not_in_list
#1 2010 67000 1 100 1
#2 2011 67001 2 101 2
#3 2012 67002 3 102 3
С помощью dplyr
:
library(dplyr)
df_to_rename %>%
rename_with(~coalesce(liste_noms_col$noms_nouveaux[match(., liste_noms_col$noms_origine)], .))