R: How to convert the output-list from a FQL-query

2019-09-04 03:22发布

问题:

I wonder how to transform a list generated by a FQL-query into a structured data frame.

I use Rfacebook to ask FQL-queries like:

getFQL("SELECT name, friends_count, sex, languages FROM user WHERE uid IN 
       (SELECT uid2 FROM friend WHERE uid1=me()), token)

This provides me with a list as output, which looks like:

[[1]]
[[1]]$name
[1] "Peter Fuller"

[[1]]$friend_count
[1] 186

[[1]]$sex
[1] "male"

[[1]]$languages
list()


[[2]]
[[2]]$name
[1] "Max Tester"

[[2]]$friend_count
[1] NULL

[[2]]$languages
[[2]]$languages[[1]]
[[2]]$languages[[1]]$id
[1] 1.056736e+14

[[2]]$languages[[1]]$name
[1] "English"


[[2]]$languages[[2]]
[[2]]$languages[[2]]$id
[1] 1.060595e+14

[[2]]$languages[[2]]$name
[1] "Italian"


[[2]]$languages[[3]]
[[2]]$languages[[3]]$id
[1] 1.144157e+14

[[2]]$languages[[3]]$name
[1] "Persian"

My aim is to convert the list into a data frame, such that the list above looks like:

          name friend_count                    languages
1 Peter Fuller          186                          NA  
2   Max Tester           NA   Englisch, Italian, Persian

Unfortunately, my efforts with unlist() and matrix failed.

回答1:

First unlist each record separately giving LL, then concatenate into a common string components with the same name using tapply and toString. Then use rbind.fill from plyr to create the final data frame:

library(plyr) # rbind.fill

LL <- lapply(L, unlist)
fun <- function(x) as.data.frame(as.list(tapply(x, names(x), toString)))
do.call(rbind.fill, lapply(LL, fun))

giving:

  friend_count         name  sex                             languages.id
1          186 Peter Fuller male                                     <NA>
2         <NA>   Max Tester <NA> 1.056736e+14, 1.060595e+14, 1.144157e+14
             languages.name
1                      <NA>
2 English, Italian, Persian

Note that we assumed this input:

L <- list(list(name = "Peter Fuller", friend_count = 186, sex = "male", 
     languages = list()),
  list(name = "Max Tester", friend_count = NULL, 
      languages = list(list(id =  1.056736e+14, name = "English"),
        list(id = 1.060595e+14, name = "Italian"),
        list(id = 1.144157e+14, name = "Persian"))))