Misconstruction
Misconstruction

Reputation: 1909

R: List of indices, including empty ones, to binary matrix

Say I have a list of indices, including elements that are empty, like:

l <- list(c(1,2,3), c(1), c(1,5), NULL, c(2, 3, 5))

Which specify the non-zero elements in a matrix, like:

(m <- matrix(c(1,1,1,0,0, 1,0,0,0,0, 1,0,0,0,5, 0,0,0,0,0, 0,1,1,0,1), nrow=5, byrow=TRUE))
     [,1] [,2] [,3] [,4] [,5]
[1,]    1    1    1    0    0
[2,]    1    0    0    0    0
[3,]    1    0    0    0    5
[4,]    0    0    0    0    0
[5,]    0    1    1    0    1

What is the fastest way, using R, to make m from l, giving that the matrix is very big, say 50.000 rows and 2000 columns?

Upvotes: 2

Views: 122

Answers (2)

akrun
akrun

Reputation: 887501

You can Filter the non-NULL list elements from 'l' and use melt to reshape it to 'data.frame' with 'key/value' columns or `row/column' index columns.

library(reshape2)
d2 <- melt(Filter(Negate(is.null), setNames(l, seq_along(l))))
Un1 <- unlist(l)
m1 <- matrix(0, nrow=length(l), ncol=max(Un1))
m1[cbind(as.numeric(d2[,2]), d2[,1])] <- 1
m1
#     [,1] [,2] [,3] [,4] [,5]
#[1,]    1    1    1    0    0
#[2,]    1    0    0    0    0
#[3,]    1    0    0    0    1
#[4,]    0    0    0    0    0
#[5,]    0    1    1    0    1

Or

 library(Matrix)
 as.matrix(sparseMatrix(as.numeric(d2[,2]), d2[,1], x=1))
 #     [,1] [,2] [,3] [,4] [,5]
#[1,]    1    1    1    0    0
#[2,]    1    0    0    0    0
#[3,]    1    0    0    0    1
#[4,]    0    0    0    0    0
#[5,]    0    1    1    0    1

Upvotes: 4

Colonel Beauvel
Colonel Beauvel

Reputation: 31171

You can do:

do.call(rbind, lapply(l, function(x) (1:max(unlist(l)) %in% x)+0L))

#     [,1] [,2] [,3] [,4] [,5]
#[1,]    1    1    1    0    0
#[2,]    1    0    0    0    0
#[3,]    1    0    0    0    1
#[4,]    0    0    0    0    0
#[5,]    0    1    1    0    1

Even if akrun solution should be faster!

Upvotes: 2

Related Questions