Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

as.data.frame flattens nested list into single row instead of creating row for each record [duplicate]

Tags:

dataframe

r

I have a nested list that looks like this:

mylist <- vector("list", 2)
mylist[[1]]$name <- "The Tucson IOT Meetup Group"
mylist[[1]]$state <- "AZ"
mylist[[2]]$name <- "#SFMySQL Meetup"
mylist[[2]]$state <- "CA"

mylist
[[1]]
[[1]]$name
[1] "The Tucson IOT Meetup Group"

[[1]]$state
[1] "AZ"


[[2]]
[[2]]$name
[1] "#SFMySQL Meetup"

[[2]]$state
[1] "CA"

I'd like to turn this into a data frame with columns "name" and "state" and two rows, one for each record. But when I try to use as.data.frame to do this, I get back a single row of data, with separate columns for each of the records' variables, like this:

myframe <- as.data.frame(mylist)
myframe
                              name state          name.1 state.1
1 The Tucson IOT Meetup Group    AZ #SFMySQL Meetup      CA

I'm not sure what's happening. What's the right way to do this?

like image 902
Traviskorte Avatar asked Sep 21 '14 19:09

Traviskorte


2 Answers

do.call(rbind.data.frame, mylist)
##                           name state
## 2  The Tucson IOT Meetup Group    AZ
## 21             #SFMySQL Meetup    CA

The do.call function is somewhat like the (l/s)apply functions and allows functions to accumulate results of successive calls. The Reduce function sometimes accomplishes the same result:

 Reduce(rbind.data.frame, mylist)
##                          name state
##2  The Tucson IOT Meetup Group    AZ
##21             #SFMySQL Meetup    CA

You can even get rbind to "work" with Reduce:

Reduce(rbind, mylist)
##     name                          state
##init "The Tucson IOT Meetup Group" "AZ" 
##     "#SFMySQL Meetup"             "CA" 

Initially thought that may be the best result. (I prefer results that deliver character values rather than factors.) However, both Reduce approaches deliver rather strange structures when viewed with str().

like image 193
IRTFM Avatar answered Nov 10 '22 05:11

IRTFM


Or try data.tables rbindlist function (very efficient for big data sets)

library(data.table)
rbindlist(mylist)
#                           name state
# 1: The Tucson IOT Meetup Group    AZ
# 2:             #SFMySQL Meetup    CA
like image 25
David Arenburg Avatar answered Nov 10 '22 06:11

David Arenburg