变量定义与mutate取决于它在前一行中的值

时间:2015-07-23 20:34:49

标签: r dplyr

我有以下格式的数据:

   time click       interaction
1   407 FALSE              TRUE
2   408  TRUE              TRUE
3   409 FALSE             FALSE
4   410 FALSE             FALSE
5   411 FALSE             FALSE
6   412 FALSE             FALSE
7   413 FALSE             FALSE
8   414 FALSE             FALSE
9   415 FALSE             FALSE
10  416 FALSE             FALSE
11  417 FALSE             FALSE
12  418 FALSE             FALSE
13  419 FALSE             FALSE
14  420 FALSE             FALSE
15  421 FALSE             FALSE
16  422 FALSE             FALSE
17  423 FALSE             FALSE
18  424 FALSE             FALSE
19  425 FALSE             FALSE
20  426 FALSE             FALSE
21  427 FALSE             FALSE
22  428 FALSE             FALSE
23  429 FALSE             FALSE
24  430 FALSE             FALSE
25  431 FALSE             FALSE
26  432 FALSE             FALSE
27  433 FALSE             FALSE
28  434 FALSE             FALSE
29  435 FALSE              TRUE
30  436 FALSE             FALSE

它表示用户每秒与应用程序交互的方式(点击和其他交互事件,如打字,滚动等,interaction,如果有任何交互,点击或其他)。我想计算一个新的变量,该变量在单击之后没有交互的范围内为真,直到它们再次开始交互为止。

所以对于这个新变量,如果有:

,我希望它是真的
  • 在最后一秒点击,在当前秒中没有互动(点击或其他),或者
  • 在最后一秒点击后没有互动,并且当前第二秒仍然没有互动。

我用dplyr尝试了类似的东西:

activity %>% mutate(
    nothing.after.click = (lag(click) == TRUE & interaction == FALSE) |
        (lag(nothing.after.click) == TRUE & interaction == FALSE)
)

但遗憾的是它无法正常工作(它表示“错误:对象'无所事事。未找到'after.click'”)。我怎样才能做到这一点?如果使用dplyr是不可能的,我会欢迎使用其他东西。

这是我想要的输出:

   time click       interaction nothing.after.click
1   407 FALSE              TRUE               FALSE
2   408  TRUE              TRUE               FALSE
3   409 FALSE             FALSE                TRUE
4   410 FALSE             FALSE                TRUE
5   411 FALSE             FALSE                TRUE
6   412 FALSE             FALSE                TRUE
7   413 FALSE             FALSE                TRUE
8   414 FALSE             FALSE                TRUE
9   415 FALSE             FALSE                TRUE
10  416 FALSE             FALSE                TRUE
11  417 FALSE             FALSE                TRUE
12  418 FALSE             FALSE                TRUE
13  419 FALSE             FALSE                TRUE
14  420 FALSE             FALSE                TRUE
15  421 FALSE             FALSE                TRUE
16  422 FALSE             FALSE                TRUE
17  423 FALSE             FALSE                TRUE
18  424 FALSE             FALSE                TRUE
19  425 FALSE             FALSE                TRUE
20  426 FALSE             FALSE                TRUE
21  427 FALSE             FALSE                TRUE
22  428 FALSE             FALSE                TRUE
23  429 FALSE             FALSE                TRUE
24  430 FALSE             FALSE                TRUE
25  431 FALSE             FALSE                TRUE
26  432 FALSE             FALSE                TRUE
27  433 FALSE             FALSE                TRUE
28  434 FALSE             FALSE                TRUE
29  435 FALSE              TRUE               FALSE
30  436 FALSE             FALSE               FALSE

最终,我们的目标是在nothing.after.click为真的情况下过滤这些行,所以如果有另一种思考这个问题的方法,我也会欢迎。

2 个答案:

答案 0 :(得分:3)

您无法在初始定义中引用变量。我们能做的就是多次通过。

当我看到你的情况时:

nothing.after.click = (lag(click) == TRUE & interaction == FALSE) |
        (lag(nothing.after.click) == TRUE & interaction == FALSE)

我在两种可能性中都看到interaction == FALSE。因此,如果interactionTRUE,那么nothing.after.click(从此处开出nac)肯定是假的。否则,我还不确定,所以我将其设置为NA。这是我的第一次传递:

dat %>% mutate(nac = ifelse(interaction, FALSE, NA))

我们已经处理了interaction == FALSE部分,下一遍将是您或子句的lag(click) == TRUE部分。对于NA的任何内容,因此尚未确定,如果lag(click)为真,则为TRUE,否则我们将保持不变。 (== TRUE是多余的,所以我把它遗漏了。)

dat %>% mutate(nac = ifelse(interaction, FALSE, NA),
               nac = ifelse(lag(click) & is.na(nac), TRUE, nac))

对于最后一次传递是lag(nac)部分,任何仍未定义的内容都将设置为先前定义的值。这是zoo:na.locf的工作(locf代表"最后一次观察结转"):

library(zoo)
dat %>% mutate(nac = ifelse(interaction, FALSE, NA),
               nac = ifelse(lag(click) & is.na(nac), TRUE, nac),
               nac = na.locf(nac))

#    time click interaction   nac
# 1   407 FALSE        TRUE FALSE
# 2   408  TRUE        TRUE FALSE
# 3   409 FALSE       FALSE  TRUE
# 4   410 FALSE       FALSE  TRUE
# 5   411 FALSE       FALSE  TRUE
# 6   412 FALSE       FALSE  TRUE
# 7   413 FALSE       FALSE  TRUE
# 8   414 FALSE       FALSE  TRUE
# 9   415 FALSE       FALSE  TRUE
# 10  416 FALSE       FALSE  TRUE
# 11  417 FALSE       FALSE  TRUE
# 12  418 FALSE       FALSE  TRUE
# 13  419 FALSE       FALSE  TRUE
# 14  420 FALSE       FALSE  TRUE
# 15  421 FALSE       FALSE  TRUE
# 16  422 FALSE       FALSE  TRUE
# 17  423 FALSE       FALSE  TRUE
# 18  424 FALSE       FALSE  TRUE
# 19  425 FALSE       FALSE  TRUE
# 20  426 FALSE       FALSE  TRUE
# 21  427 FALSE       FALSE  TRUE
# 22  428 FALSE       FALSE  TRUE
# 23  429 FALSE       FALSE  TRUE
# 24  430 FALSE       FALSE  TRUE
# 25  431 FALSE       FALSE  TRUE
# 26  432 FALSE       FALSE  TRUE
# 27  433 FALSE       FALSE  TRUE
# 28  434 FALSE       FALSE  TRUE
# 29  435 FALSE        TRUE FALSE
# 30  436 FALSE       FALSE FALSE

答案 1 :(得分:1)

已经有一个很好的答案(+1),但这里有一个使用基础R的替代方案。

dat$nac <- with(dat, unlist(
    sapply(split(interaction, cumsum(interaction & click)), function(x) c(F, !cumsum(x[-1])))
))

#    time click interaction   nac
# 1   407 FALSE        TRUE FALSE
# 2   408  TRUE        TRUE FALSE
# 3   409 FALSE       FALSE  TRUE
# 4   410 FALSE       FALSE  TRUE
# 5   411 FALSE       FALSE  TRUE
# 6   412 FALSE       FALSE  TRUE
# 7   413 FALSE       FALSE  TRUE
# 8   414 FALSE       FALSE  TRUE
# 9   415 FALSE       FALSE  TRUE
# 10  416 FALSE       FALSE  TRUE
# 11  417 FALSE       FALSE  TRUE
# 12  418 FALSE       FALSE  TRUE
# 13  419 FALSE       FALSE  TRUE
# 14  420 FALSE       FALSE  TRUE
# 15  421 FALSE       FALSE  TRUE
# 16  422 FALSE       FALSE  TRUE
# 17  423 FALSE       FALSE  TRUE
# 18  424 FALSE       FALSE  TRUE
# 19  425 FALSE       FALSE  TRUE
# 20  426 FALSE       FALSE  TRUE
# 21  427 FALSE       FALSE  TRUE
# 22  428 FALSE       FALSE  TRUE
# 23  429 FALSE       FALSE  TRUE
# 24  430 FALSE       FALSE  TRUE
# 25  431 FALSE       FALSE  TRUE
# 26  432 FALSE       FALSE  TRUE
# 27  433 FALSE       FALSE  TRUE
# 28  434 FALSE       FALSE  TRUE
# 29  435 FALSE        TRUE FALSE
# 30  436 FALSE       FALSE FALSE

这里的诀窍是使用点击和互动同时发生的事实。然后split这些事件的数据,并使用cumsum查找点击之间互动的变化。