Search code examples
rtransformationdplyrmutated

dplyr transmute returning fewer rows than the original data frame


I need to get a summary of a grouped data set that is 4 rows (basically the square the would surround the set of data points in the subet of the data frame.

A function:

myfun <- function(F1,F2){

  out <-structure(list(f2 = c(1097.81431421448, 2331.43870452636, 2154.84583430979, 
1210.68973077198), f1 = c(411.462078942253, 334.070858898298, 
834.761924536241, 782.569047430496)), .Names = c("f2", "f1"), row.names = c(NA, 
4L), class = "data.frame")
  return(out)
}

a data set:

pb2 <-
structure(list(Type = structure(c(2L, 2L, 2L, 2L, 2L, 2L, 2L, 
2L, 2L, 2L, 2L, 2L, 2L, 2L, 2L, 2L, 2L, 2L, 2L, 2L), .Label = c("c", 
"m", "w"), class = "factor"), Sex = structure(c(2L, 2L, 2L, 2L, 
2L, 2L, 2L, 2L, 2L, 2L, 2L, 2L, 2L, 2L, 2L, 2L, 2L, 2L, 2L, 2L
), .Label = c("f", "m"), class = "factor"), Speaker = c("1", 
"1", "1", "1", "1", "1", "1", "1", "1", "1", "1", "1", "1", "1", 
"1", "1", "1", "1", "1", "1"), Vowel = structure(c(8L, 8L, 7L, 
7L, 5L, 5L, 2L, 2L, 3L, 3L, 1L, 1L, 4L, 4L, 9L, 9L, 10L, 10L, 
6L, 6L), .Label = c("aa", "ae", "ah", "ao", "eh", "er", "ih", 
"iy", "uh", "uw"), class = "factor"), IPA = structure(c(9L, 9L, 
7L, 7L, 4L, 4L, 1L, 1L, 8L, 8L, 2L, 2L, 3L, 3L, 6L, 6L, 10L, 
10L, 5L, 5L), .Label = c("\\ae", "\\as", "\\ct", "\\ef", "\\er\\hr", 
"\\hs", "\\ic", "\\vt", "i", "u"), class = "factor"), F0 = c(160L, 
186L, 203L, 192L, 161L, 155L, 140L, 180L, 144L, 148L, 148L, 170L, 
161L, 158L, 163L, 190L, 160L, 157L, 177L, 164L), F1 = c(240L, 
280L, 390L, 310L, 490L, 570L, 560L, 630L, 590L, 620L, 740L, 800L, 
600L, 660L, 440L, 400L, 240L, 270L, 370L, 460L), F2 = c(2280L, 
2400L, 2030L, 1980L, 1870L, 1700L, 1820L, 1700L, 1250L, 1300L, 
1070L, 1060L, 970L, 980L, 1120L, 1070L, 1040L, 930L, 1520L, 1330L
), F3 = c(2850L, 2790L, 2640L, 2550L, 2420L, 2600L, 2660L, 2550L, 
2620L, 2530L, 2490L, 2640L, 2280L, 2220L, 2210L, 2280L, 2150L, 
2280L, 1670L, 1590L)), .Names = c("Type", "Sex", "Speaker", "Vowel", 
"IPA", "F0", "F1", "F2", "F3"), row.names = c(NA, 20L), class = "data.frame")

Using dplyr to make the summary..:

library(dplyr)

> pb %>% group_by(Type,Sex) %>% transmute(F1=myfun(F1,F2)["f1"]) 
Source: local data frame [1,520 x 3]
Groups: Type, Sex

   Type Sex       F1
1     m   m <dbl[4]>
2     m   m <dbl[4]>
3     m   m <dbl[4]>
4     m   m <dbl[4]>
5     m   m <dbl[4]>
6     m   m <dbl[4]>
7     m   m <dbl[4]>
8     m   m <dbl[4]>
9     m   m <dbl[4]>
10    m   m <dbl[4]>

The function returns a data frame column, but these are not appended together the way I expected them to. How do I make these values stack on top of each other?


Solution

  • You're almost there. Just unnest what you've got:

     library(tidyr)
     pb2 %>% 
       group_by(Type,Sex) %>% 
       transmute(F1=myfun(F1,F2)["f1"]) %>% 
       unnest(F1)
    

    Output:

    # Source: local data frame [80 x 3]
    # 
    #    Type Sex       F1
    # 1     m   m 411.4621
    # 2     m   m 334.0709
    # 3     m   m 834.7619
    # 4     m   m 782.5690
    # 5     m   m 411.4621
    # 6     m   m 334.0709
    # 7     m   m 834.7619
    # 8     m   m 782.5690
    # 9     m   m 411.4621
    # 10    m   m 334.0709
    # ..  ... ...      ...