如何对mutliple列进行累积逻辑运算

时间:2015-07-02 10:45:16

标签: r xts

我在xts对象中有很多列,我想在第一列中找到一定数量以上的百分比,第一列或第二列中的百分比高于某个数字,百分比是任何数字在某个数字之上的前三列等等。

我目前正在手动执行此操作,如下所示:

library(xts)
set.seed(69) 
x = xts( cbind( v.1 = runif(20)*100,  v.2 = runif(20)*100,   v.3 = runif(20)*100,   v.4 = runif(20)*100), Sys.Date()-20:1 )

c(
  mean( x$v.1 > 50),
  mean( x$v.1 > 50 | x$v.2 > 50) ,
  mean( x$v.1 > 50 | x$v.2 > 50 | x$v.3 > 50) ,
  mean( x$v.1 > 50 | x$v.2 > 50 | x$v.3 > 50 | x$v.4 > 50)
  )

这给出了这个示例输出:

[1] 0.50 0.70 0.80 0.95

但现在我想推广到任意数量的列,而不仅仅是v.1v.4。所以我正在寻找像这样的单一功能:

this_is_mean( x, c('v.1','v.2','v.3','v.4'), 50)

或者看起来像是:

mean ( foo( x, c('v.1','v.2','v.3','v.4'), 50) )

(我当然会使用paste('v',1:N,sep='.')作为列名称)

3 个答案:

答案 0 :(得分:3)

您似乎应该可以使用sapplyrowSums(如果我理解您的问题):

sapply(1:ncol(x), function(y) mean(rowSums(x[, seq(y)] > 50) >= 1))
## [1] 0.50 0.70 0.80 0.95

如果需要,使用vapply(1:ncol(x), function(y) mean(rowSums(x[, seq(y)] > 50) >= 1), numeric(1L))可以提高速度。

答案 1 :(得分:3)

这是另一个替代方案,似乎比@ AnadaMahto的解决方案(在此示例中)快一点。您可能还会发现它更直接。

R> rowMeans(apply(x > 50, 1, cumsum) >= 1)
 v.1  v.2  v.3  v.4 
0.50 0.70 0.80 0.95

虽然请注意rowMeans只对数据进行一次传递。与mean不同,后者进行2次传递(一次用于浮点算术纠错)。

答案 2 :(得分:1)

我们也可以通过矩阵乘法来实现:

colSums(((x>50) %*% !lower.tri(diag(ncol(x))))>0) / nrow(x)

通过对角矩阵进行乘法选择第一列,前两列,依此类推。我把它比作

rowMeans(apply(x > 50, 1, cumsum) >= 1)

它看起来更快,尽管表达方式更加丑陋。

相关问题