我想将下面伪代码中显示的内容加速到R中最快的代码(矢量化,或任何比简单for循环更快的方法)。
成像我有一个4维数组A
(任意填充1只作为例子):
A = array(runif(nx*ny*nz*nt), c(nx,ny,nz,nt))
并且我希望以更快的速度循环(填充output
数组,该数组具有比其先前值更累积的第二维度...更像是第二维的累积乘积输入A
数组:
output = array(1, c(nx, ny+1, nz, nt))
for (x in 1:nx)
{
for (z in 1:nz)
{
for (t in 1:nt)
{
for (y in 2:(ny+1))
{
output[x,y,z,t] = output[x,y-1,z,t] * (1 - A[x,y-1,z,t])
}
}
}
}
我怎样才能更快地完成这项工作?使用apply()
?或者一些最后有abind()
的智能累积产品?
答案 0 :(得分:2)
您当然可以使用data_p
和apply
来获得相同的结果(cumprod
是必要的,因为apply调用的函数的结果在第一维中结束):
aperm
将结果与output1 <- aperm(apply(A,c(1,3,4),function(v) cumprod(1-v)),c(2,1,3,4))
进行比较,差异非常接近output
:
.Machine$double.eps
请注意,> max(abs(output[,2:11,,]-output1))
[1] 1.110223e-16
> .Machine$double.eps
[1] 2.220446e-16
不包含output1
,但此矩阵只包含以下内容:
output[,1,,]
因此,如果需要,可以轻松扩展> all(output[,1,,]==1)
[1] TRUE
。
对于output1
,这种方法显然更好:
nx = ny = nz = nt = 10
然后nx = ny = nz = nt = 10
A = array(runif(nx*ny*nz*nt), c(nx,ny,nz,nt))
f.old <- function(){
output = array(1, c(nx, ny+1, nz, nt))
for (x in 1:nx)
{
for (z in 1:nz)
{
for (t in 1:nt)
{
for (y in 2:(ny+1))
{
output[x,y,z,t] = output[x,y-1,z,t] * (1 - A[x,y-1,z,t])
}
}
}
}
}
f.new <- function() aperm(apply(A,c(1,3,4),function(v) cumprod(1-v)),c(2,1,3,4))
产生(在我的机器上):
microbenchmark