2016-10-14 8 views
2

Предположим, что у меня есть dataframe так:конкатенации всех строк в пределах группы с помощью dplyr

hand_id card_id card_name card_class 
A  1  p   alpha 
A  2  q   beta 
A  3  r   theta 
B  2  q   beta 
B  3  r   theta 
B  4  s   gamma 
C  1  p   alpha 
C  2  q   beta 

Я хотел бы сцепить card_id, card_name и card_class в один ряд на уровне рук A, B, C . Таким образом, результат будет выглядеть примерно так:

hand_id combo_1 combo_2 combo_3 
A  1-2-3 p-q-r alpha-beta-theta 
B  2-3-4 q-r-s beta-theta-gamma 
.... 

Я попытался сделать это с помощью group_by и мутировать, но я не могу заставить его работать

data <- read_csv('data.csv') 
    byHand <- group_by(data, hand_id) %>% 
     mutate(combo_1 = paste(card_id), 
      combo_2 = paste(card_name), 
      combo_3 = paste(card_class)) 

Благодарим за помощь.

ответ

5

Вы были отчасти близко!

library(tidyr) 
library(dplyr) 

data <- read_csv('data.csv') 
byHand <- group_by(data, hand_id) %>% 
    summarise(combo_1 = paste(card_id, collapse = "-"), 
       combo_2 = paste(card_name, collapse = "-"), 
       combo_3 = paste(card_class, collapse = "-")) 

или с помощью summarise_each:

byHand <- group_by(data, hand_id) %>% 
     summarise_each(funs(paste(., collapse = "-"))) 
+1

Спасибо, zacdav, это работает! – user7016618

+2

'summaryise_each' будет устаревать в пользу' summaryise_all', который вы можете использовать аналогично или как 'df%>% group_by (hand_id)%>% summaryise (вставить, свернуть = '-')' – alistaire

0

не очень хорошо знакомы с dplyr ... так вот моя попытка без dplyr

df <- read_csv('data.csv') 

res <- lapply(split(df, df$hand_id),function(x){ 
    sL <- apply(x[,-1], 2, function(y) paste(y, collapse = "-")) 
    d <- data.frame(x$hand_id[1], rbind(sL)) 
    names(d) <- c("hand_id", "combo_1", "combo_2", "combo_3") 
    return(d) 
}) 
res <- do.call("rbind",res) 
rownames(res) <- NULL 

Вот результат:

## hand_id combo_1 combo_2   combo_3 
## 1  A 1-2-3 p-q-r alpha-beta-theta 
## 2  B 2-3-4 q-r-s beta-theta-gamma 
## 3  C  1-2  p-q  alpha-beta 
+1

'aggregate' удобно:.' Агрегат (~ hand_id, lapply (ДФ, as.character), FUN = function (x) {paste (x, collapse = '-')}) ' – alistaire

2

Вот еще один вариант использования data.table

library(data.table) 
setDT(data)[, lapply(.SD, paste, collapse="-") , by = hand_id] 
#  hand_id card_id card_name  card_class 
#1:  A 1-2-3  p-q-r alpha-beta-theta 
#2:  B 2-3-4  q-r-s beta-theta-gamma 
#3:  C  1-2  p-q  alpha-beta