さらに 2 つの解決策:
1つ目は、質問の例の修正です
do.call("rbind", rep(list(A), n))
2 つ目は、行列の展開、複製、再構築です。
matrix(rep(t(A),n), ncol=ncol(A), byrow=TRUE)
効率性が求められているため、ベンチマークが必要
library("rbenchmark")
A <- matrix(1:15, nrow=3)
n <- 10
benchmark(rbind(A, A, A, A, A, A, A, A, A, A),
do.call("rbind", replicate(n, A, simplify=FALSE)),
do.call("rbind", rep(list(A), n)),
apply(A, 2, rep, n),
matrix(rep(t(A),n), ncol=ncol(A), byrow=TRUE),
order="relative", replications=100000)
与える:
test replications elapsed
1 rbind(A, A, A, A, A, A, A, A, A, A) 100000 0.91
3 do.call("rbind", rep(list(A), n)) 100000 1.42
5 matrix(rep(t(A), n), ncol = ncol(A), byrow = TRUE) 100000 2.20
2 do.call("rbind", replicate(n, A, simplify = FALSE)) 100000 3.03
4 apply(A, 2, rep, n) 100000 7.75
relative user.self sys.self user.child sys.child
1 1.000 0.91 0 NA NA
3 1.560 1.42 0 NA NA
5 2.418 2.19 0 NA NA
2 3.330 3.03 0 NA NA
4 8.516 7.73 0 NA NA
したがって、最速は生の呼び出しですが、それは固定されており、事前にわかってrbind
いることを前提としています。n
が固定されていない場合n
、最速はdo.call("rbind", rep(list(A), n)
です。これらは、3x5 マトリックスと 10 回の複製用でした。行列のサイズが異なると、順序が異なる場合があります。
編集:
n=600 の場合、結果は異なる順序になります (明示的なrbind
バージョンは除外されます)。
A <- matrix(1:15, nrow=3)
n <- 600
benchmark(do.call("rbind", replicate(n, A, simplify=FALSE)),
do.call("rbind", rep(list(A), n)),
apply(A, 2, rep, n),
matrix(rep(t(A),n), ncol=ncol(A), byrow=TRUE),
order="relative", replications=10000)
与える
test replications elapsed
4 matrix(rep(t(A), n), ncol = ncol(A), byrow = TRUE) 10000 1.74
3 apply(A, 2, rep, n) 10000 2.57
2 do.call("rbind", rep(list(A), n)) 10000 2.79
1 do.call("rbind", replicate(n, A, simplify = FALSE)) 10000 6.68
relative user.self sys.self user.child sys.child
4 1.000 1.75 0 NA NA
3 1.477 2.54 0 NA NA
2 1.603 2.79 0 NA NA
1 3.839 6.65 0 NA NA
明示的なrbind
バージョンを含めると、バージョンよりわずかに速くなりますがdo.call("rbind", rep(list(A), n))
、大幅には変わらず、apply
またはmatrix
バージョンよりも遅くなります。したがって、この場合、任意への一般化n
は速度の低下を必要としません。