Thaler, Thorn, LAUSANNE, Applied Mathematics
2010-Jul-20 09:29 UTC
[R] apply: return list of matrices
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),
c=c(1,0,0,1,1,1,0,1,1,1,1,1))
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]]
[,1] [,2]
[1,] 1 1
[2,] 0 2
[[2]]
[,1] [,2]
[1,] 0 2
[2,] 0 2
[[3]]
[,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)
matrix(unlist(x),2,2))
However, is an additional lapply call really necessary?
Thanks 4 ur input,
Thorn
one approach is the following:
ddf <- data.frame(a = rep(1:4,3), b = rep(paste("p", 1:3,
sep=""),
each=4), c = c(1,0,0,1,1,1,0,1,1,1,1,1))
sp <- lapply(split(ddf$c, ddf$b), factor, levels = 0:1)
combn(sp, 2, FUN = table, simplify = FALSE)
I hope it helps.
Best,
Dimitris
On 7/20/2010 11:29 AM, Thaler, Thorn, LAUSANNE, Applied Mathematics
wrote:> 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),
> c=c(1,0,0,1,1,1,0,1,1,1,1,1))
>
> 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]]
> [,1] [,2]
> [1,] 1 1
> [2,] 0 2
>
> [[2]]
> [,1] [,2]
> [1,] 0 2
> [2,] 0 2
>
> [[3]]
> [,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)
> matrix(unlist(x),2,2))
>
> However, is an additional lapply call really necessary?
>
> Thanks 4 ur input,
>
> Thorn
>
> ______________________________________________
> R-help at r-project.org mailing list
> https://stat.ethz.ch/mailman/listinfo/r-help
> PLEASE do read the posting guide
http://www.R-project.org/posting-guide.html
> and provide commented, minimal, self-contained, reproducible code.
>
--
Dimitris Rizopoulos
Assistant Professor
Department of Biostatistics
Erasmus University Medical Center
Address: PO Box 2040, 3000 CA Rotterdam, the Netherlands
Tel: +31/(0)10/7043478
Fax: +31/(0)10/7043014