[R] apply: return list of matrices

Thaler, Thorn, LAUSANNE, Applied Mathematics Thorn.Thaler at rdls.nestle.com
Tue Jul 20 11:29:11 CEST 2010

Hi everybody,

Suppose we have the following data structure:

ddf <-data.frame(a=rep(1:4,3), b=rep(paste("p", 1:3, sep=""), each=4),

I want now to make a contingency table for each pair of values of p,
i.e. a contingency table for each of the pairs (p1,p2), (p1,p3) and
(p2,p3). The result should be given as a list of matrices: 

# [[1]] <=> (p1, p2)
# [[2]] <=> (p1, p3)
# [[3]] <=> (p2, p3)
     [,1] [,2]
[1,]    1    1
[2,]    0    2

     [,1] [,2]
[1,]    0    2
[2,]    0    2

     [,1] [,2]
[1,]    0    1
[2,]    0    3

Basically, I achieved what I want except that the output format is not
the way it should be:

ct <- function(bc) {
  n <- length(bc)
  bc <- factor(bc)
  table(bc[1:(n/2)], bc[(n/2+1):n])

ct returns a 2x2 table giving the contingency counts.

f <- function(p, b) {
  allC <- t(combn(levels(as.factor(p)), 2))
  bRaw <- apply(allC, 1, function(x) cbind(b[p==x[1]], b[p==x[2]]))
  # bRaw would preferable be already a list of nx2 matrices, but apply
coerces the result to a single matrix, 
  # whose columns are rbind(b[p==x[1]], b[p==x[2]]), that's why "ct"
takes just one argument and splits the vector

  apply(bRaw, 2, ct)

Again the result is one single matrix instead of list of matrices (the
columns consist of the values of the matrices). I suppose that apply
does some sophisticated simplification on the result vector, but how can
I circumvent this mechanism? For the time being I made another *apply
call, which gives me the same result in the format I'd like: just
replace the last line in function f by

lapply(apply(bRaw, 2, function(x) list(ct(x))), function(x)

However, is an additional lapply call really necessary?

Thanks 4 ur input,


More information about the R-help mailing list