R - 基于前一行在每第n行插入一个True

时间:2018-03-29 20:02:55

标签: r rollapply

测试数据框架:

a<-data.frame(True_False = c(T,F,F,F,F,T,F,T,T,T,F,F,F,F,F,F,F,F))
  True_False
1        TRUE
2       FALSE
3       FALSE
4       FALSE
5       FALSE
6        TRUE
7       FALSE
8        TRUE
9        TRUE
10       TRUE
11      FALSE
12      FALSE
13      FALSE
14      FALSE
15      FALSE
16      FALSE
17      FALSE
18      FALSE

使用这个,我想编辑这个列或创建一个新的,每隔三行至少有一次True。意思是我需要检查当前行,如果为False,如果前两行为False,则将其设为True。否则保持原样。使用Zoo,Dplyr和Rollapply,我得到了接近。

library(zoo)
library(tidyverse)
    b<-a%>%
  mutate(Roll = ifelse(rollapplyr(Input,3,sum, partial = T) == 0,T,Input))
b$Desired<-c(T,F,F,T,F,T,F,T,T,T,F,F,T,F,F,T,F,F)

   Input  Roll Desired
1   TRUE  TRUE    TRUE
2  FALSE FALSE   FALSE
3  FALSE FALSE   FALSE
4  FALSE  TRUE    TRUE
5  FALSE  TRUE   FALSE
6   TRUE  TRUE    TRUE
7  FALSE FALSE   FALSE
8   TRUE  TRUE    TRUE
9   TRUE  TRUE    TRUE
10  TRUE  TRUE    TRUE
11 FALSE FALSE   FALSE
12 FALSE FALSE   FALSE
13 FALSE  TRUE    TRUE
14 FALSE  TRUE   FALSE
15 FALSE  TRUE   FALSE
16 FALSE  TRUE    TRUE
17 FALSE  TRUE   FALSE
18 FALSE  TRUE   FALSE

基本上我的问题是它会将总和折叠成整列,然后添加真则。因此,我们拥有不必要的真理。那么有没有办法在进入下一行之前应用True?我假设我需要使用某种类型的应用,但这是我不熟悉的领域,甚至阅读文档我不知道如何直接执行此操作。

3 个答案:

答案 0 :(得分:1)

看起来你需要这样的东西。这是一种方法(不是最干净的):

a<-data.frame(True_False = c(T,F,F,F,F,T,F,T,T,T,F,F,F,F,F,F,F,F))
a$Desired<-NA
a$Desired[4:nrow(a)]<-sapply(4:nrow(a),function(z){
  if(z%%3==1 & a$True_False[z]==F & a$True_False[z-1]==F & a$True_False[z-2]==F){a$True_False[z]<-T}else{a$True_False[z]}
})
a$Desired[1:3]<-a$True_False[1:3]

答案 1 :(得分:1)

由于您需要动态更新矢量以处理进一步的操作,我会说一个简单的for - 循环是要走的路:

for(i in 3:nrow(a)){
  a$True_False[i] <- ifelse(sum(a$True_False[(i-2):i]) == 0, T, a$True_False[i])
}

> a
   True_False
1        TRUE
2       FALSE
3       FALSE
4        TRUE
5       FALSE
6        TRUE
7       FALSE
8        TRUE
9        TRUE
10       TRUE
11      FALSE
12      FALSE
13       TRUE
14      FALSE
15      FALSE
16       TRUE
17      FALSE
18      FALSE

答案 2 :(得分:1)

定义更新功能f并通过Reduce运行。

f <- function(x, i) {
  if (i >= 3 && all(!x[seq(to = i, length = 3)])) x[i] <- TRUE
  x
}
transform(a, new = Reduce(f, init = True_False, seq_along(True_False)))

,并提供:

   True_False   new
1        TRUE  TRUE
2       FALSE FALSE
3       FALSE FALSE
4       FALSE  TRUE
5       FALSE FALSE
6        TRUE  TRUE
7       FALSE FALSE
8        TRUE  TRUE
9        TRUE  TRUE
10       TRUE  TRUE
11      FALSE FALSE
12      FALSE FALSE
13      FALSE  TRUE
14      FALSE FALSE
15      FALSE FALSE
16      FALSE  TRUE
17      FALSE FALSE
18      FALSE FALSE