Skip to content
Prev 310450 / 398506 Next

as.data.frame(do.call(rbind, lapply)) produces something weird

Your call to rbind() creates matrix of mode "list".  Thus every element
can be of a different type, although you "know" that there is a pattern
to the types.  E.g.,
  > R <- rbind(
          list(Letter="a", Integer=1L, Complex=1+1i),
          list(Letter="b", Integer=2L, Complex=2+2i))
  > str(R)
  List of 6
   $ : chr "a"
   $ : chr "b"
   $ : int 1
   $ : int 2
   $ : cplx 1+1i
   $ : cplx 2+2i
   - attr(*, "dim")= int [1:2] 2 3
   - attr(*, "dimnames")=List of 2
    ..$ : NULL
    ..$ : chr [1:3] "Letter" "Integer" "Complex"

data.frame(R), since R is a matrix, will make a data.frame containing
the columns of R.  It does not decide that since each column is a list
that it should what data.frame(list(...)) would do, it just sticks those
columns, as is, into the data.frame that it creates:

  > Rdf <- data.frame(R)
  > str(Rdf)
  'data.frame':   2 obs. of  3 variables:
   $ Letter :List of 2
    ..$ : chr "a"
    ..$ : chr "b"
   $ Integer:List of 2
    ..$ : int 1
    ..$ : int 2
   $ Complex:List of 2
    ..$ : cplx 1+1i
    ..$ : cplx 2+2i

You can convert those columns to their "natural" type, at least
the type of their first element, with

  > for(i in seq_along(Rdf)) Rdf[[i]] <- as(Rdf[[i]], class(Rdf[[i]][[1]]))
  > str(Rdf)
  'data.frame':   2 obs. of  3 variables:
   $ Letter : chr  "a" "b"
   $ Integer: int  1 2
   $ Complex: cplx  1+1i 2+2i

Note the as(list(...), atomicType) does the conversion if every element
of list(...) has length 1 and throws an error otherwise.  That is probably
a good check in this case.  unlist() would give the same result, perhaps
more quickly, if the list has the structure you expect but would silently
give bad results if some element of the list did not have length one.

Is that what you are looking for?

Note that storing things in a list takes a lot more memory  than storing
them as atomic vectors so your technique may not scale up very well.
  > object.size(as.list(1:1e6)) / object.size(1:1e6)
  13.9998700013 bytes

Bill Dunlap
Spotfire, TIBCO Software
wdunlap tibco.com