2017-01-29 20 views
0

Взятия данных кадра DF, Я хотел бы извлечь уникальныйзначения в соответствии со следующим предпочтительным условьте й на каждый поля:Как извлечь уникальный элемент по набору предпочтенных условий

1- если С1 существует, извлечь соответствующее значение и игнорировать остальные

2-, если С2 существует, извлечь соответствующий ва ЛУЭ и игнорировать другие

... и так далее до C5

данные:

df <- data.frame (Field=rep(c("F1","F2","F3","F4","F5"),each=3), 
       Cond=rep(c("C1","C2","C3","C4","C5"),3), 
       Value=c(1:15)) 

желаемая выход:

output <- data.frame (F= c("F1","F2","F3","F4","F5"), 
        C= c("C1","C1","C2","C1","C3"), 
        Value= c(1,6,7,11,13)) 

(Примечание 1: значения были установлены как таковые в качестве примера, то реальные данные значения не упорядочены)

(Примечание 2: реальный условный столбец не в алфавитном порядке на всех. я должен был иметь что-то вроде, если A существует, чем выбрал значение «A», в противном случае переходите к следующему условию «если существует B ...» и т. д.)

+0

Можно принимать значения в 'C' сортируются? –

+0

@ Roman, нет ... значения были установлены как таковые в качестве примера примера – Rui

ответ

1

Другой вариант заключается в использовании data.table

library(data.table) 
setDT(df)[order(Field, Cond), head(.SD, 1), by = Field] 
# Field Cond Value 
#1: F1 C1  1 
#2: F2 C1  6 
#3: F3 C2  7 
#4: F4 C1 11 
#5: F5 C3 13 
+0

да, это действительно работает, если «Конд» сортируется по алфавиту. однако, если столбец «сортировка» не упорядочен в алфавитном порядке, этот пример не будет работать. – Rui

+0

@Rui В этом случае преобразуйте его в 'factor' и укажите' levels' в порядке, который вы хотите 'order (Поле, коэффициент (Cond, levels = lvl))' – akrun

2

Если вы можете сортировать data.frame перед обработкой , это довольно легко. Обратите внимание, что это работает для этого конкретного случая. Если ваши значения Cond меняются, сортировка по алфавиту может выйти из окна.

library(dplyr) 
df <- data.frame (Field=rep(c("F1","F2","F3","F4","F5"),each=3), 
        Cond=rep(c("C1","C2","C3","C4","C5"),3), 
        Value=c(1:15)) 

df <- df[with(df, order(Field, Cond)), ] 
res <- df %>% 
    group_by(Field) %>% 
    filter(row_number() == 1) 

Source: local data frame [5 x 3] 
Groups: Field [5] 

    Field Cond Value 
    <fctr> <fctr> <int> 
1  F1  C1  1 
2  F2  C1  6 
3  F3  C2  7 
4  F4  C1 11 
5  F5  C3 13 

Вот еще один, более общий способ сделать это. Порядок сортировки определен в so (см. this question). Обратите внимание, как я искал значения для Cond, чтобы показать, что он не сортируется в алфавитном порядке.

df <- data.frame (Field=rep(c("F1","F2","F3","F4","F5"),each=3), 
        Cond=rep(c("rg1","kl2","xy3","rq4","ab5"),3), 
        Value=c(1:15)) 

so <- c("rg1","kl2","xy3","rq4","ab5") 

df %>% 
    group_by(Field) %>% 
    slice(match(so, Cond)) %>% 
    filter(row_number() == 1) 

    Field Cond Value 
    <fctr> <fctr> <int> 
1  F1 rg1  1 
2  F2 rg1  6 
3  F3 kl2  7 
4  F4 rg1 11 
5  F5 xy3 13 
+0

действительно, вы правы, я думаю, что это будет проблемой. Мой «условный» столбец не упорядочен в алфавитном порядке вообще. У меня было что-то вроде, если A существует, чем выбрал «Значение», в противном случае переходите к следующему условию «если существует B ...» и т. Д. – Rui

+0

@Rui Я изменил свой ответ, и я думаю, что он должен работать ваш общий случай сейчас. –

+0

@ Roman. Отлично, он отлично работает. Большое спасибо – Rui