Как использовать срез в dplyr, чтобы сохранить строки со значениями NA в R - PullRequest
1 голос
/ 05 августа 2020

У меня есть следующий набор данных, и я хочу знать минимальное слово для каждой группы, и если минимального слова нет (это NA), я все равно хочу его отображать

df=data.frame(
  key=c("A","A","B","B","C"),
  word=c(1,2,3,5,NA))

df%>%group_by(key)%>%slice(which.min(word))

Это исключает key = C, word = NA, который мне нужен:

df_out=data.frame(
  key=c("A","B","C"),
  word=c(1,3,NA))

Ответы [ 3 ]

1 голос
/ 05 августа 2020

Мы можем проверить условие с помощью if. Если all word в группе равно NA, мы возвращаем первую строку или возвращаем минимальную строку.

library(dplyr)

df %>%
  group_by(key)%>%
  slice(if(all(is.na(word))) 1L else which.min(word))

# key    word
#  <chr> <dbl>
#1 A         1
#2 B         3
#3 C        NA

Другой вариант - набрать arrange данные по word и выбрать 1-ю строку в каждой группе.

df %>% arrange(key, word) %>% group_by(key) %>% slice(1L)
1 голос
/ 05 августа 2020

Мы можем создать логическое условие с is.na в filter и также вернуть NA строки после группировки по 'ключу'

library(dplyr)
df %>%
     group_by(key) %>% 
     filter(word == min(word)|is.na(word))

Или используя slice. Нам не нужны if/else условие

df %>%
    group_by(key) %>% 
    slice(which(word ==min(word)|is.na(word)))
# A tibble: 3 x 2
# Groups:   key [3]
#  key    word
#  <chr> <dbl>
#1 A         1
#2 B         3
#3 C        NA

Или более компактно

df %>%
    group_by(key) %>% 
    slice(match(min(word), word))
# A tibble: 3 x 2
# Groups:   key [3]
#  key    word
#  <chr> <dbl>
#1 A         1
#2 B         3
#3 C        NA

ПРИМЕЧАНИЕ. Использование match возвращает индекс первого совпадения.

which.min удаляет NA

which.min(c(NA, 1, 3))
#[1] 2
0 голосов
/ 05 августа 2020

Вы также можете arrange по word и использовать distinct из dplyr, чтобы получить желаемый результат.

library(dplyr)
df %>% 
    arrange(word) %>% 
    distinct(key, .keep_all = TRUE)
#  key word
#1   A    1
#2   B    3
#3   C   NA
...