R 根据条件计算平均值

R 根据条件计算平均值,r,dataframe,R,Dataframe,下面是我的数据框 Row_ID A B 1 0 0 2 0 0 3 0 0 4 0 1 5 0 1 6 0 1 7 62.75 0 8 100 0 9 100 0 10 10

下面是我的数据框

    Row_ID  A      B  
       1   0       0  
       2   0       0  
       3   0       0  
       4   0       1  
       5   0       1  
       6   0       1  
       7  62.75    0  
       8  100      0  
       9  100      0 
      10  100     -1 
      11  100     -1  
      12  100     -1  
      13  100     -1   
      14  87.625  -1  
      15   0       0  
      16   0       0  
      17   0       1   
      18   0       1  
      19   10      1    
      20   13.43   1
      21   67.31   0  
      22   86.5    0
      23   99      0  
      24   99      0  
      25   99      0 
我需要在以下条件下,每连续5行计算
A
的平均值。
B
中的值
1和-1
是两种过渡状态

aa的平均值基于
B
中的值

b平均计算中要考虑的
A
中的数据点从
b
中过渡结束的最后一个数据点开始。(例如:
B
中的转换在
行ID=6
处结束,因此在计算平均值时必须考虑
A
的第7、8、9、10和11行)

c参考上述示例,尽管
B
的第10行和第11行的值有变化,但在计算平均值时应考虑
A
中相应的行,因为在上一次迭代的平均值计算中考虑了这些值

是否有不使用
embed()
函数的变通代码,因为我的数据大约有900K个值,而且由于
embed()
创建了矩阵,所以内存使用不会那么理想

预期产出

    Row_ID  A      B   Avg  
       1   0       0     0  
       2   0       0     0  
       3   0       0     0  
       4   0       1     0  
       5   0       1     0  
       6   0       1     0  
       7  62.75    0     92.55  
       8  100      0     92.55  
       9  100      0     92.55 
      10  100     -1     92.55 
      11  100     -1     92.55  
      12  100     -1     0  
      13  100     -1     0   
      14  87.625  -1     0  
      15   0       0     2  
      16   0       0     2  
      17   0       1     2   
      18   0       1     2  
      19   10      1     2    
      20   13.43   1     0
      21   67.31   0     90.16  
      22   86.5    0     90.16
      23   99      0     90.16  
      24   99      0     90.16  
      25   99      0     90.16

我们可以使用
data.table

library(data.table)
setDT(df1)[, Avg := mean(A)*(.N>4), cumsum(c(TRUE,  diff(abs(B)!=1)==1))]
df1
#    Row_ID  A  B  Avg
# 1:      1  0  0  0.0
# 2:      2  5  1  0.0
# 3:      3  6  1  0.0
# 4:      4  8  1  0.0
# 5:      5  9  0 10.2
# 6:      6  8  0 10.2
# 7:      7 15 -1 10.2
# 8:      8 17 -1 10.2
# 9:      9  2 -1 10.2
#10:     10  6  0  0.0
#11:     11  9  0  0.0
#12:     12  8 -1  0.0
#13:     13  5 -1  0.0
#14:     14  2  0  6.4
#15:     15  9  0  6.4
#16:     16  2  1  6.4
#17:     17  9  1  6.4
#18:     18 10  1  6.4
或者通过@thelatemail进行访问

setDT(df1)[,  Avg := mean(A) *(.N > 4) , (rleid(B) + 1) %/% 2]
更新 根据这个新的例子,也许这会有所帮助

setDT(df2)[, Avg := c(rep(mean(head(A, 5)), 5), rep(0, .N-5)), 
        cumsum(c(TRUE,  diff(abs(B)!=1)==1))]
df2
#    Row_ID       A  B    Avg
# 1:      1   0.000  0  0.000
# 2:      2   0.000  0  0.000
# 3:      3   0.000  0  0.000
# 4:      4   0.000  1  0.000
# 5:      5   0.000  1  0.000
# 6:      6   0.000  1  0.000
# 7:      7  62.750  0 92.550
# 8:      8 100.000  0 92.550
# 9:      9 100.000  0 92.550
#10:     10 100.000 -1 92.550
#11:     11 100.000 -1 92.550
#12:     12 100.000 -1  0.000
#13:     13 100.000 -1  0.000
#14:     14  87.625 -1  0.000
#15:     15   0.000  0  2.000
#16:     16   0.000  0  2.000
#17:     17   0.000  1  2.000
#18:     18   0.000  1  2.000
#19:     19  10.000  1  2.000
#20:     20  13.430  1  0.000
#21:     21  67.310  0 90.162
#22:     22  86.500  0 90.162
#23:     23  99.000  0 90.162
#24:     24  99.000  0 90.162
#25:     25  99.000  0 90.162

为什么第1-4行的平均值等于0而不是4.75?@LateMail我假设它是基于5个连续元素的,第一种情况是,它只有4个元素,然后是5个,然后又是4个,..@t如问题中所述,平均计算所考虑的数据点应从
B
中的过渡值结束处开始,
B
中的值
0
不被视为状态,因此,在
B
中,转换结束于
行ID 4
,因此平均值计算从
5
开始到下一个连续的5行。根据新的示例更新了帖子主题的一个变体-
dat[,avg:=if(.N>=5)mean(a),by=(rleid(B)+1)%/%2]
@akrun和@thelatemail,感谢您的解决方案。。对于我在问题中给出的数据框架,它工作得非常好。但我的实际数据集并非如此。不考虑用于计算平均值的连续5行。我的意思是计算所有值的平均值,直到下一次转换更改。将其缩小到上面的数据框,在
行ID 6~1的
平均列中打印
6
@ANmike我认为您的示例不是一个很好的复制示例,它模仿了原始示例dataset@akrun是的,你说得对,我将用我的原始数据集更新我的问题。@akrun非常感谢,完全按照要求工作。