Итак, у меня есть этот фрейм данных, в котором некоторые строки дублируются в столбце «Виды», а некоторые нет. NA есть во всех типах строк, как дублированных, так и не дублированных.
Species | A | B |
--------------------------------
Tilapia guineensis | 1 | 10 |
Tilapia guineensis | 1 | NA |
Tilapia zillii | 3 | 23 |
Tilapia zillii | 3 | NA |
Eutrigla gurnardus | 18 | 4 |
Caramila artida | 9 | NA |
Sprattus sprattus | 7 | 6 |
Spalili burcant | 11 | NA |
Я хочу удалить те строки, которые имеют NA в столбце B, но только если они принадлежат повторяющейся строке. Мой вывод будет примерно таким:
Species | A | B |
--------------------------------
Tilapia guineensis | 1 | 10 |
Tilapia zillii | 3 | 23 |
Eutrigla gurnardus | 18 | 4 |
Caramila artida | 9 | NA |
Sprattus sprattus | 7 | 6 |
Spalili burcant | 11 | NA |
По сути, если строка дублируется в столбце «Виды» и имеет NA в столбце B, я хочу удалить эту строку с NA. Однако, если строка в столбце Species уникальна, я хочу сохранить ее, даже если она имеет NA.
Извините, если путаю, заранее спасибо.
Воспроизводимый формат данных:
df <- read.csv(text = "
Species,A,B
Tilapia guineensis,1,10
Tilapia guineensis,1,NA
Tilapia zillii,3,23
Tilapia zillii,3,NA
Eutrigla gurnardus,18,4
Caramila artida,9,NA
Sprattus sprattus,7,6
Spalili burcant,11,NA")
Вы можете выбрать строку, если есть только 1 строка для Species
или если это не значение NA
.
library(dplyr)
df %>% group_by(Species) %>% filter(n() == 1 | !is.na(B))
# Species A B
# <chr> <int> <int>
#1 Tilapia guineensis 1 10
#2 Tilapia zillii 3 23
#3 Eutrigla gurnardus 18 4
#4 Caramila artida 9 NA
#5 Sprattus sprattus 7 6
#6 Spalili burcant 11 NA
Вы также можете написать ту же логику в базе R и data.table
:
#Base R
subset(df, ave(!is.na(B), Species, FUN = function(x) length(x) == 1 | x))
#data.table
library(data.table)
setDT(df)[, .SD[.N == 1 | !is.na(B)], Species]
данные
df <- structure(list(Species = c("Tilapia guineensis", "Tilapia guineensis",
"Tilapia zillii", "Tilapia zillii", "Eutrigla gurnardus", "Caramila artida",
"Sprattus sprattus", "Spalili burcant"), A = c(1L, 1L, 3L, 3L,
18L, 9L, 7L, 11L), B = c(10L, NA, 23L, NA, 4L, NA, 6L, NA)), row.names = c(NA,
-8L), class = "data.frame")
Я думаю, вы можете избежать использования какой-либо логики группировки и получить результат за один проход:
df[!(duplicated(df$Species) & is.na(df$B)),]
# Species A B
#1 Tilapia guineensis 1 10
#3 Tilapia zillii 3 23
#5 Eutrigla gurnardus 18 4
#6 Caramila artida 9 NA
#7 Sprattus sprattus 7 6
#8 Spalili burcant 11 NA