У меня есть столбец в фрейме данных, содержащий темы:
sub <- c("A", "A", "B", "C", "C", "C", "D", "E", "F", "F")
subjects <- data.frame(sub)
У меня есть другой фрейм данных, содержащий столбцы предметов (где предметы находятся только в одном столбце):
one <- c("A", "C", "F")
two <- c("B", "D", NA)
three <- c("E", NA, NA)
newsubjects <- data.frame(one, two, three)
Я хочу переименовать предметы в первом кадре данных в имя столбца, найденное во втором кадре данных, соответствующем этому предмету.
Так, например, я хочу, чтобы предметы A, C и F в первом кадре данных были переименованы в «один». Выполнение этого вручную заняло бы много времени, поэтому я надеюсь, что есть способ использовать столбцы во втором фрейме данных для этого.
Я пробовал кучу вещей с forcats::fct_recode и уровнями, но ничего не работает, потому что я неправильно использую эти функции. Например, одна из моих попыток IIRC выглядела примерно так:
subjects %>%
mutate(new_var = forcats::fct_recode(sub,
!!! setNames(as.character(subjects$sub), newsubjects$one)))
Что я знаю, совершенно неправильно. Часть проблемы заключается в том, что мне трудно сформулировать свою проблему таким образом, чтобы получить релевантные результаты поиска. Спасибо за любую помощь, которую вы можете предоставить, я ценю это.





Если вы измените форму newsubjects дольше, вы можете соединить две таблицы:
library(tidyverse)
subjects %>%
left_join(newsubjects %>%
pivot_longer(everything(), names_to = "new_sub", values_to = "sub"))
Joining, by = "sub"
sub new_sub
1 A one
2 A one
3 B two
4 C one
5 C one
6 C one
7 D two
8 E three
9 F one
10 F one
Используя purrr::map(), создайте список, сочетающий имена столбцов со значениями из newsubjects. Затем распакуйте это внутри forcats::fct_collapse(), чтобы перекодировать значения в subjects.
library(purrr)
library(forcats)
new_ids <- map(newsubjects, ~ .x[!is.na(.x)])
subjects$sub <- fct_collapse(subjects$sub, !!!new_ids)
subjects
sub
1 one
2 one
3 two
4 one
5 one
6 one
7 two
8 three
9 one
10 one
На основе равной длины в одном, двух, трех вы также можете создать поиск
library(dplyr)
sub <- c("A", "A", "B", "C", "C", "C", "D", "E", "F", "F")
subjects <- data.frame(sub)
one <- c("A", "C", "F")
two <- c("B", "D", NA)
three <- c("E", NA, NA)
additions <- c(one, two, three)
lookup <- data.frame(
sub = additions %>% unlist(),
value = rep(1:length(additions), each=length(additions[[1]])))
subjects %>% inner_join(lookup) %>% select(value)
В базе R:
gsub("\\d", "", names(unlist(newsubjects))[match(subjects$sub, unlist(newsubjects))])
Это работает с моим репрексом, но не тогда, когда я пытаюсь применить его к своим фактическим данным. Столбец «new_sub» просто заполнен NA. Мой фактический столбец «sub» составляет 14 000 строк (содержащих смесь тем и NA), в то время как столбцы в фрейме данных «newsubjects» составляют от 14 до 76 строк (и более короткие из них дополнены NA). Есть ли что-то очевидное, что мне нужно изменить при переводе на мои фактические данные?