【问题标题】:R apply function over consecutive values of two vectorsR 在两个向量的连续值上应用函数
【发布时间】:2018-12-13 17:21:59
【问题描述】:

我正在尝试对两个向量的连续值应用函数。问题可以简化为:

x = c(2,4,6,8,10)
y = c(1,2,3,4,5)

for (i in 1:(length(x)-1)) {
    a = mean(x[i:(i+1)])
    b = mean(y[i:(i+1)])
    print(a/b)
}

我想知道通过使用apply 系列中的函数来做同样的事情,有什么更有效的方法?谢谢!

【问题讨论】:

标签: r vector apply


【解决方案1】:

好吧,也许是显而易见的,但是:

(x[-1] + x[-length(x)]) / (y[-1] + y[-length(x)])
# [1] 2 2 2 2

(这比 Onyambu 基准测试中的 COLMEANS 解决方案快 15 倍)

【讨论】:

  • 不错。当数据变大时,如果stats::filter() 的滚动平均值没有更快(比 colMeans 更快),我也会感到非常惊讶。像马蒂在这里的回答 - stackoverflow.com/a/4862334/496803
【解决方案2】:

你可以使用基础 R:

a = sapply(1:(length(x)-1),function(x)x:(x+1))
colMeans(structure(x[a],.Dim=dim(a)))/colMeans(structure(y[a],.Dim=dim(a)))
[1] 2 2 2 2

甚至

 tapply(x[a], col(a), mean)/tapply(y[a], col(a), mean)

这些基本函数似乎比 rollapply 运行得更快,因为 rollapply 会执行两次 rollapply:

microbenchmark::microbenchmark(
   COLMEANS={a=sapply(1:(length(x)-1),function(x)x:(x+1))
   colMeans(structure(x[a],.Dim=dim(a)))/
     colMeans(structure(y[a],.Dim=dim(a)))},
   ROLLAPPLY=rollapply(x,2,mean)/rollapply(y,2,mean),
   TAPPLY={a=sapply(1:(length(x)-1),function(x)x:(x+1))
     tapply(x[a], col(a), mean)/tapply(y[a], col(a), mean)
   },
   ROLLMEANS=rollmean(x,2) / rollmean(y,2)
 )
 Unit: microseconds
      expr      min        lq      mean   median        uq      max neval
  COLMEANS   76.517  109.0040  187.7223  138.499  178.0405 4598.685   100
 ROLLAPPLY 1752.185 1954.8040 2144.2619 2028.543 2211.9260 6244.430   100
    TAPPLY  398.827  519.3725  665.5016  604.224  682.4505 5304.859   100
ROLLMEANS 1366.610 1619.6715 1815.3349 1731.0260 1957.7965 2615.240   100

【讨论】:

  • 这是一个很好的答案!谢谢!但是,一般来说,如果该函数不是简单的意思,而是“手工制作”的,您可以在 a 的实例上使用另一个 apply 吗?
【解决方案3】:
library(zoo)
rollmean(x,2) / rollmean(y,2)

【讨论】:

    【解决方案4】:

    您可以使用 zoo 库中的 rollapply:

      library(zoo)
      rollapply(x,2,mean)/rollapply(y,2,mean)
    

    【讨论】:

      猜你喜欢
      • 2021-10-05
      • 1970-01-01
      • 2017-11-07
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-08-27
      • 2015-08-19
      • 1970-01-01
      相关资源
      最近更新 更多