#r #dataframe #dplyr
Вопрос:
Представьте, что у меня есть фрейм данных, который выглядит следующим образом:
df <- data.frame(
name1 = c("John", "Jake", "Ann", "Mary", "Harry"),
name2 = c("Jake", "John", "Mary", "Ann", "Mary"),
value = c(2, 4, 6, 8, 10)
)
Я хочу создать новый фрейм данных, который суммируется value
по любым строкам, где name1
и name2
и одинаково, независимо от их порядка. Так что мой результат был бы:
result <- data.frame(
name1 = c("John", "Ann", "Harry"),
name2 = c("Jake", "Mary", "Mary"),
value = c(6, 14, 10)
)
Есть какие-нибудь умные идеи, желательно с использованием tidyverse? Большое спасибо!
Ответ №1:
Вы можете использовать pmin
и pmax
которые сортируют данные в алфавитном порядке и принимают sum
value
.
library(dplyr)
df %>%
group_by(nam1 = pmin(name1, name2), nam2 = pmax(name1, name2)) %>%
summarise(value = sum(value), .groups = 'drop')
# nam1 nam2 value
# <chr> <chr> <dbl>
#1 Ann Mary 14
#2 Harry Mary 10
#3 Jake John 6
Ответ №2:
Опция с igraph
пакетом
library(igraph)
get.data.frame(
simplify(
graph_from_data_frame(df, directed = FALSE),
edge.attr.comb = sum
)
)
дает
from to value
1 John Jake 6
2 Ann Mary 14
3 Mary Harry 10
Ответ №3:
Мы можем использовать
library(data.table)
setDT(df)[,.(value = sum(value)), by = .(nam1 = pmin(name1, name2), nam2 = pmax(name1, name2))]