Я использую пакет labelled
и пытаюсь установить пользовательские пропущенные значения. У меня есть фрейм данных, в котором я хочу установить отсутствующие значения для списка определенных столбцов, а не для всего набора данных.
В настоящее время мне нужно ввести каждый столбец (s2 и s3). Есть ли более эффективный способ? В моем полном наборе данных есть десятки столбцов.
df <- tibble(s1 = c(1, 2, 3, 9), s2 = c(1, 1, 2, 9), s3 = c(1, 1, 2, 9))
df <- df %>%
set_na_values(., s2 = 9) %>%
set_na_values(., s3 = 9)
na_values(df$s1)
na_values(df$s2)
na_values(df$s3)
Как будет выглядеть последний (названный вектор и его сплайсинг)?
В качестве простого примера, если вы хотите установить 9 пользователей, отсутствующих для каждого столбца, вы можете сделать df %>% set_na_values(!!!setNames(rep(9, ncol(.)), names(.)))
. Хитрость будет заключаться в построении вектора, который будет применяться только к интересующим столбцам, но вам нужно будет расширить свой вопрос, если вам нужна помощь в этом отношении.
Я бы хотел, чтобы вектор применялся только к s2 и s3, но не к s1.
nm <- setdiff(names(df), "s1"); df %>% set_na_values(!!!setNames(rep(9, length(nm)), nm))
Функция set_na_values()
принимает несколько пар, поэтому вам не нужно вызывать ее более одного раза:
library(labelled)
library(dplyr)
df %>%
set_na_values(s2 = 9, s3 = 9)
Если вы имели дело с большим количеством переменных, вы могли бы программно создать именованный вектор или список (если для каждой переменной имеется несколько пропущенных значений) и соединить их внутри функции. Если из вашего комментария вы хотели применить его ко всему, кроме переменной s1
, вы можете сделать:
nm <- setdiff(names(df), "s1")
df %>%
set_na_values(!!!setNames(rep(9, length(nm)), nm))
# A tibble: 4 x 3
s1 s2 s3
<dbl> <dbl+lbl> <dbl+lbl>
1 1 1 1
2 2 1 1
3 3 2 2
4 9 9 (NA) 9 (NA)
В качестве альтернативы вы можете использовать labelled_spss()
и воспользоваться преимуществами across()
, которые допускают семантику tidyselect
(но это перезапишет любые существующие помеченные значения):
df %>%
mutate(across(-s1, labelled_spss, na_values = 9))
# A tibble: 4 x 3
s1 s2 s3
<dbl> <dbl+lbl> <dbl+lbl>
1 1 1 1
2 2 1 1
3 3 2 2
4 9 9 (NA) 9 (NA)
Чтобы сбросить любые существующие значения, используйте:
df %>%
mutate(across(-s1, ~ labelled_spss(.x, labels = val_labels(.x), na_values = 9)))
Я проверил это, и это работает. Дополнительный вопрос: вместо указания отрицательного значения (s1 — это столбец, к которому я не хочу применять NA), как мне указать положительное значение (s2 и s3 — столбцы, к которым я хочу применить NA), используя именованный векторный подход? @ричи-сакраменто
Вы можете использовать что-то вроде setNames(rep(9, 2), paste0("s", 2:3))
- трудно сказать без дополнительной информации.
Функция принимает несколько пар, поэтому вам не нужно вызывать ее более одного раза, например.
df %>% set_na_values(s2 = 9, s3 = 9)
или, если вы имели дело с большим количеством переменных, вы могли бы программно создать именованный вектор и соединить его внутри функции.