2017-01-12 7 views
0

У меня есть кадр данных следующего типа:Значения под колонной комбинации

date  ID1 ID2 sum 
2017-1-5 1  a  200 
2017-1-5 1  b  150 
2017-1-5 2  a  300 
2017-1-4 1  a  200 
2017-1-4 1  b  120 
2017-1-4 2  a  300 
2017-1-3 1  b  150 

Я пытаюсь сравнить между комбинациями столбцов над разными датами, чтобы увидеть, если sum значение равно. Итак, в приведенном выше примере я хотел бы, чтобы код идентифицировал, что сумма [ID1=1, ID2=b] комбинация отличается между 2017-1-5 и 2017-1-4 (В моих реальных данных у меня есть более 2 ID категорий и более 2 Dates).

Я хочу, чтобы мой вывод был фреймом данных, который содержит все комбинации, которые включают (по крайней мере один) неравные результаты. В моем примере:

date  ID1 ID2 sum 
2017-1-5 1  b  150 
2017-1-4 1  b  120 
2017-1-3 1  b  150 

я пытался решить его с помощью петли, как это: Is there a R function that applies a function to each pair of columns без большого успеха.

Ваша помощь будет оценена по достоинству.

+0

Что вы хотите, чтобы ваш результат выглядел? Если у вас более двух дат для комбинации идентификаторов, вы просто хотите указать, что они все одинаковые или нет? Или вы хотите идентифицировать уникальные, или что? – aichao

+0

Я хочу ** обозначить ** комбинацию, в которой сумма не была равна; например, кадр данных, который будет выглядеть следующим образом: (rows; 'date') и (столбцы,' ID1', 'ID2',' sum') ... поэтому в моем примере: (1-я строка = '2017-1 -5') (2-я строка = '2017-1-4') и (1-й столбец =' ID1') (2-й столбец = 'ID2') (3-й кол =' сумма') ... и 2 ячейки будут показывать 150 и 120. Надеюсь, это было ясно. Я мог бы изменить свой вопрос. – staove7

+0

Что делать, если у вас три даты, а у двух из них одна и та же сумма, а третья - нет? Какой из двух вы хотите добавить в свой выход? – aichao

ответ

0

Используя dplyr, мы можем group_by_(.dots=paste0("ID",1:2)), а затем увидеть, если значения unique:

library(dplyr) 
res <- df %>% group_by_(.dots=paste0("ID",1:2)) %>% 
       mutate(flag=(length(unique(sum))==1)) %>% 
       ungroup() %>% filter(flag==FALSE) %>% select(-flag) 

group_by_ позволяет группировать ID столбцы легко. Просто измените 2 на сколько-нибудь много столбцов ID (т. Е. N) вы считаете, что они нумеруются последовательно от 1 до N. Столбец flag создан, чтобы указать, являются ли все значения одинаковыми (то есть число unique значений равно 1). Затем мы получаем filter для получения результатов, для которых flag==FALSE. Это дает желаемый результат:

res 
### A tibble: 3 x 4 
##  date ID1 ID2 sum 
##  <chr> <int> <chr> <int> 
##1 2017-1-5  1  b 150 
##2 2017-1-4  1  b 120 
##3 2017-1-3  1  b 150 
+0

Amazing. Благодаря! Еще одна вещь. Есть ли способ «отмечать» только различия, большие, чем sum integer; например, больше 50 (что в моем примере не даст никаких результатов)? – staove7

+0

Если вы заинтересованы в том, чтобы пометить диапазон значений 'sum', который больше, чем' 50' в каждой группе, тогда вы можете использовать 'flag = (max (sum) -min (sum)) <= 50' вместо' flag = (length (unique (sum)) == 1) 'внутри' mutate'. Это установит те группы, где диапазон значений 'sum' меньше или равен' 50' 'TRUE', так что будут сохраняться только те, у кого есть группы с диапазонами более 50. – aichao

+0

Удивительно снова. Огромное спасибо! – staove7