Извлечение индексов строк, где существуют дублированные пары, и значений этих строк, которые отличаются - PullRequest
0 голосов
/ 03 января 2019

У меня есть датафрейм ниже:

master <- data.frame(A=c(1,1,2,2,3,3,4,4,5,5), B=c(1,2,3,3,4,5,6,6,7,8),C=c(5,2,5,7,7,5,7,9,7,8),D=c(1,2,5,3,7,5,9,6,7,0))

Как видите, у меня есть 4 столбца A,B,C,D.Чего я хочу добиться, так это создать новый фрейм данных, который будет содержать дублированные пары строк между A и B, индекс строк, в которых происходит такое дублирование, и имена столбцов, которые делают эти строки различными (C,D,или C и D) в третьем столбце.Чтобы сделать мой запрос более понятным, я показываю пример с master2 вместо master, который включает только A и B

master2 <- data.frame(A=c(1,1,2,2,3,3,4,4,5,5), B=c(1,2,3,3,4,5,6,6,7,8))

, а затем с:

library(data.table)
setDT(master2)

master2[master2[, .N, by=names(master2)][ N > 1L ], on=names(master2), 
  .(N, locs = .(.I)), by=.EACHI]

Я получаю:

#    A B N locs
# 1: 2 3 2  3,4
# 2: 4 6 2  7,8

Поэтому я хочу, чтобы эта логика была реализована в master фрейме данных, а также добавила еще один столбец с именем «Different» с именами столбцов, которые отличают эти строки.Если строки идентичны всем, тогда новый столбец с именами столбцов, которые отличаются, должен принимать значение «ничто». Если возможно добавить другой столбец с начальной позицией столбца «Другой».Это будет 3 для C и 4 для D?

Требуемый результат должен быть примерно таким:

# A tibble: 2 x 4
# Groups:   A [?]
#     A     B     n locs  different position
#   <dbl> <dbl> <int> <chr> <chr>    <int>
#1     2     3     2 3, 4  C, D     3,4
#2     4     6     2 7, 8  C, D     3,4

1 Ответ

0 голосов
/ 03 января 2019

Если нам нужен индекс строки, то создайте столбец последовательности ('rn'), сгруппированный по интересующим столбцам, оставьте только группы, у которых число строк больше 1, summarise, чтобы получить количество строк (n()), а также paste ed индекс последовательности строк для группы.Что касается «другого» столбца, то не совсем понятно логика.Здесь реализовано одно из них, основанное на вхождении различных значений в пределах одной и той же группы «А» и «В» с case_when

library(tidyverse)
master %>%
   mutate(rn = row_number()) %>% 
   group_by(A, B) %>% 
   filter(n() > 1) %>% 
   summarise(n = n(), 
            locs =  toString(rn),
            Different = case_when(n_distinct(C) > 1 & n_distinct(D) > 1 ~ 'C, D', 
                                  n_distinct(C) > 1 ~ 'C', 
                                  n_distinct(D) > 1 ~ 'D', 
                                  TRUE ~ 'Same')) 
# A tibble: 2 x 4
# Groups:   A [?]
#     A     B     n locs  different
#   <dbl> <dbl> <int> <chr> <chr>    
#1     2     3     2 3, 4  C, D     
#2     4     6     2 7, 8  C, D     

Обновление

На основе комментариев для включения'позиция'

master %>%
    mutate(rn = row_number()) %>% 
    group_by(A, B) %>% 
    filter(n() > 1) %>% 
    mutate(position = toString(rn[!(duplicated(paste(C, D))| 
              duplicated(paste(C, D), fromLast = TRUE))])) %>%
    summarise(n = n(), 
             locs =  toString(rn),
             Different = case_when(n_distinct(C) > 1 & n_distinct(D) > 1 ~ 'C, D', 
                                   n_distinct(C) > 1 ~ 'C', 
                                   n_distinct(D) > 1 ~ 'D', 
                                   TRUE ~ 'Same'),
             position = first(position))
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...