R - 识别连续序列

时间:2015-07-15 19:23:06

标签: r sequence

我有一个包含107635行和3列的大文件:主题,感兴趣区域(ROI)和试用次数。 ROI可以是A,B,C,D,E,F。 我想要做的只是保留那些在ROI列中我有连续B,C,D序列的试验,这是B第一次出现。 B,C和D出现的次数无关紧要。

在下面的例子中,我可以保留ntrial 78和201,因为B首次出现之后是C和D. 但是,我需要删除ntrial 10和400.在试验中10 B,C和D不连续。在试验400第一次出现B时,B后面没有C和D.

对于输出,我只需要一个值为1的列,以便在每行中保留试验,并且对应于要删除的试验的行,需要值为0。

有关如何创建可自动执行此过程的代码的任何建议,而不会直观地检查每个试验?

非常感谢!

subject ROI ntrial output
sbj05   A   78     1
sbj05   A   78     1
sbj05   A   78     1
sbj05   A   78     1
sbj05   A   78     1
sbj05   A   78     1
sbj05   B   78     1
sbj05   B   78     1
sbj05   C   78     1
sbj05   D   78     1
sbj05   E   78     1
sbj05   E   78     1
sbj05   E   78     1
sbj05   A   201    1
sbj05   A   201    1
sbj05   A   201    1
sbj05   A   201    1
sbj05   A   201    1
sbj05   B   201    1
sbj05   C   201    1
sbj05   D   201    1
sbj05   E   201    1
sbj05   E   201    1
sbj05   E   201    1
sbj05   F   201    1
sbj05   F   201    1
sbj05   A   10     0
sbj05   A   10     0
sbj05   A   10     0
sbj05   A   10     0
sbj05   B   10     0
sbj05   A   10     0
sbj05   C   10     0
sbj05   D   10     0
sbj05   E   10     0
sbj05   E   10     0
sbj05   A   400    0
sbj05   A   400    0
sbj05   A   400    0
sbj05   B   400    0
sbj05   A   400    0
sbj05   B   400    0
sbj05   C   400    0
sbj05   C   400    0
sbj05   C   400    0
sbj05   D   400    0
sbj05   E   400    0
sbj05   E   400    0
sbj05   D   400    0

3 个答案:

答案 0 :(得分:4)

以下是使用data.tablestringi

的尝试

首先,我正在定义一些辅助函数,它将帮助我检测每组B的第一个精度,并验证它们后面跟着正确的序列

Myfunc <- function(x) {
               which(x == "B")[1L] == 
               stri_locate_first_regex(paste(x, collapse = ""), 'B*CD')[, 1L]
              } 

然后,实施是直截了当的

library(data.table)
library(stringi)
setDT(df)[, if(Myfunc(ROI)) .SD, by = .(subject, ntrial)]
#     subject ntrial ROI
#  1:   sbj05     78   A
#  2:   sbj05     78   A
#  3:   sbj05     78   A
#  4:   sbj05     78   A
#  5:   sbj05     78   A
#  6:   sbj05     78   A
#  7:   sbj05     78   B
#  8:   sbj05     78   B
#  9:   sbj05     78   C
# 10:   sbj05     78   D
# 11:   sbj05     78   E
# 12:   sbj05     78   E
# 13:   sbj05     78   E
# 14:   sbj05    201   A
# 15:   sbj05    201   A
# 16:   sbj05    201   A
# 17:   sbj05    201   A
# 18:   sbj05    201   A
# 19:   sbj05    201   B
# 20:   sbj05    201   C
# 21:   sbj05    201   D
# 22:   sbj05    201   E
# 23:   sbj05    201   E
# 24:   sbj05    201   E
# 25:   sbj05    201   F
# 26:   sbj05    201   F

或者,如果您只想要一个额外的列,那么

setDT(df)[, output := +Myfunc(ROI), by = .(subject, ntrial)]

答案 1 :(得分:1)

这是另一个:

idx <- sapply(split(df, df$ntrial), function(x) { 
  B <- with(rle(x$ROI == "B"),  sum(lengths[seq(which.max(values))]))
  all(x$ROI[B:(B+2)] == c("B", "C", "D"))
})
subset(df, ntrial %in% names(which(idx)))

答案 2 :(得分:0)

使用base Rmatch的{​​{1}}方式:

rle

没有对齐的列让我烦恼