Для работы в списке и вызвать функцию на всех объектах, do.call
моя обычная первая идея, наряду с cbind
здесь, чтобы связать по столбцам все объекты.
Для n=100
(с другими ответами для полноты картины):
n <- 10
nr <- 24
nc <- 8000
test <- list()
set.seed(1234)
for (i in 1:n){
test[[i]] <- matrix(rnorm(nr*nc),nr,nc)
}
require(data.table)
ori <- function() { matrix(as.numeric(unlist(test)) ,nr,nc*n) }
Tensibai <- function() { do.call(cbind,test) }
BrodieG <- function() { `attr<-`(do.call(c, test), "dim", c(nr, nc * n)) }
nicola <- function() { setattr(unlist(test),"dim",c(nr,nc*n)) }
library(microbenchmark)
microbenchmark(r1 <- ori(),
r2 <- Tensibai(),
r3 <- BrodieG(),
r4 <- nicola(), times=10)
Результаты:
Unit: milliseconds
expr min lq mean median uq max neval cld
r1 <- ori() 23.834673 24.287391 39.49451 27.066844 29.737964 93.74249 10 a
r2 <- Tensibai() 17.416232 17.706165 18.18665 17.873083 18.192238 21.29512 10 a
r3 <- BrodieG() 6.009344 6.145045 21.63073 8.690869 10.323845 77.95325 10 a
r4 <- nicola() 5.912984 6.106273 13.52697 6.273904 6.678156 75.40914 10 a
Что касается почему (в комментариях), @nicola сделал дать ответ об этом, есть меньше копии, чем оригинальный метод.
Все методы дает тот же результат:
> identical(r1,r2,r3,r4)
[1] TRUE
Возможно, попробуйте 'do.call (cbind, test)' – Tensibai
@ Tensibai Спасибо, я попробовал, и это действительно намного быстрее. Будет обновлено мое сообщение соответственно. Любая интуиция, почему она намного быстрее? – Bayesric
Меньше всего копия и литье. Я думаю, – Tensibai