2013-04-18 23 views
4

数据:在初审有条件的子集数据R

row A B 
1 1 1 
2 1 1 
3 1 2 
4 1 3 
5 1 1 
6 1 2 
7 1 3 

大家好!我想要做的(上面的例子)是在列A中求和这些值,但只有当列B = 1(所以从一个简单的子集行开始 - 下面)。

sum(data$A[data$B==1]) 

不过,我只想做这个条件出现,直到值切换第一时间。如果该条件在列后面重新出现(示例中的第5行),我对它不感兴趣!

我真的很感谢你的帮助(我怀疑是简单的)问题!

回答

1

使用data.table语法优雅,你可以使用rle得到这个工作

library(data.table) 
DT <- data.table(data) 
DT[ ,B1 := { 
    bb <- rle(B==1) 
    r <- bb$values 
    r[r] <- seq_len(sum(r)) 
    bb$values <- r 
    inverse.rle(bb) 
} ] 

DT[B1 == 1, sum(a)] 
# [1] 2 
1

这里是这样做的一个相当复杂的方式:

data$counter = cumsum(data$B == 1) 
sum(data$A[(data$counter >= 1:nrow(data) - sum(data$counter == 0)) & 
      (data$counter != 0)]) 
1

另一种方式:

idx <- which(data$B == 1) 
sum(data$A[idx[idx == (seq_along(idx) + idx[1] - 1)]]) 
# [1] 2 

# or alternatively 
sum(data$A[idx[idx == seq(idx[1], length.out = length(idx))]]) 
# [1] 2 

的想法:一是获得1。这里所有的指标是c(2,3,5)。从起始索引=“2”开始,您希望获得所有连续(或连续的)索引,即c(2,3,4,5...)。所以,从2拿这么多连续的数字并将它们等同起来。当他们不连续时,他们不会是平等的。也就是说,一旦出现不匹配,所有其他以下数字也会出现不匹配。所以,匹配相等的前几个数字将只是那些“连续的”(这是你所期望的)。

+0

我不认为这个工程。尝试一下例如:'set.seed(1); data = data.frame(A = 1,B = as.integer(runif(100,1,4)))'。我用你的公式得到9(而不是1)。 – eddi

+0

@Eddi,非常真实。做了编辑。应该现在工作。谢谢指出。 – Arun