计算R中数据帧的每一行中特定值的连续出现次数

时间:2015-06-03 16:55:10

标签: r dataframe

对于许多位置(这么多行)我有一个data.frame变量的月值,我想计算值为零的连续月数(即连续单元格) 。如果只是从左到右阅读,这将很容易,但增加的复杂性是,年底是连续到年初。

例如,在下面缩短的示例数据集中(有季节而不是几个月),位置1有3' 0' 0月份,位置2有2个,3个没有。

df<-cbind(location= c(1,2,3),
Winter=c(0,0,3),
Spring=c(0,2,4),
Summer=c(0,2,7),
Autumn=c(3,0,4))

如何计算这些连续的零值?我看过rle,但我目前还不是更聪明的人!

非常感谢任何帮助:)

2 个答案:

答案 0 :(得分:2)

您已经确定了最长跑可以采取的两种情况:(1)中间某处或(2)在每一行的结束和开始之间分开。因此,您想要计算每个条件并采用最大值:

df<-cbind(
Winter=c(0,0,3),
Spring=c(0,2,4),
Summer=c(0,2,7),
Autumn=c(3,0,4))

#>      Winter Spring Summer Autumn
#> [1,]      0      0      0      3
#> [2,]      0      2      2      0
#> [3,]      3      4      7      4


# calculate the number of consecutive zeros at the start and end
startZeros  <-  apply(df,1,function(x)which.min(x==0)-1)
#> [1] 3 1 0
endZeros  <-  apply(df,1,function(x)which.min(rev(x==0))-1)
#> [1] 0 1 0

# calculate the longest run of zeros
longestRun  <-  apply(df,1,function(x){
                y = rle(x);
                max(y$lengths[y$values==0],0)}))
#> [1] 3 1 0

# take the max of the two values
pmax(longestRun,startZeros +endZeros  )
#> [1] 3 2 0

当然更简单的解决方案是:

longestRun  <-  apply(cbind(df,df),# tricky way to wrap the zeros from the start to the end
                      1,# the margin over which to apply the summary function
                      function(x){# the summary function
                          y = rle(x);
                          max(y$lengths[y$values==0],
                              0)#include zero incase there are no zeros in y$values
                      })

请注意,上述解决方案有效,因为我的df不包含location字段(列)。

答案 1 :(得分:2)

试试这个:

df <- data.frame(location = c(1, 2, 3),
                 Winter = c(0, 0, 3),
                 Spring = c(0, 2, 4),
                 Summer = c(0, 2, 7),
                 Autumn = c(3, 0, 4))

maxcumzero <- function(x) {
    l <- x == 0
    max(cumsum(l) - cummax(cumsum(l) * !l))
}

df$N.Consec <- apply(cbind(df[, -1], df[, -1]), 1, maxcumzero)

df
#   location Winter Spring Summer Autumn N.Consec
# 1        1      0      0      0      3        3
# 2        2      0      2      2      0        2
# 3        3      3      4      7      4        0

这会在数据帧中添加一列,指定在数据帧的每一行中连续出现零的最大次数。数据框是自身的列绑定,以便能够检测秋冬之间的连续零。

此处使用的方法基于Martin Morgan的answer to this similar question