R - поиск числовых последовательностей - PullRequest
2 голосов
/ 13 марта 2019

У меня есть фрейм данных, похожий на этот:

   nr  grp start stop l1 ratio
   11   1   300  350  +   1.0                  
   12   1   400  450  -   0.8                  
   13   1    50  550  +   1.0                  
   14   1   600  650  -   1.0                  
   21   1   800  850  -   1.0                  
   36   1  1000 1050  +   0.0       
   37   1  1100 1200  +   0.9
   38   1  1250 1300  -   0.7
   39   1  1350 1400  +   1.0

и мне нужно найти последовательности последовательных чисел и переместить их в новый df. Мне нужно вытащить всю первую строку последовательности и заменить только значение для столбца остановки, взятого из последней строки последовательности.

Конечный df должен выглядеть так:

  nr  grp start stop l1 ratio
  11   1   300  650   +   1.0                  
  36   1   1000 1400  -   0.8 

Я пытался сделать это так:

t1<- read.table('aa.txt',sep = "\t", header=TRUE)
head(t1)
t1$chk <- NA
dl <- length(t1$nr)
for (i in 1:dl){
  if(isTRUE(t1$nr[i]+1 == t1$nr[i+1])){
  t1$chk[i] <- "t"  
  }else{
    t1$chk[i] <- 'F'
    }
}

и я получаю это:

   nr  grp start stop l1 ratio chk
   11   1   300  350  +   1.0   t             
   12   1   400  450  -   0.8   t              
   13   1    50  550  +   1.0   t              
   14   1   600  650  -   1.0   F              
   21   1   800  850  -   1.0   F              
   36   1  1000 1050  +   0.0   t   
   37   1  1100 1200  +   0.9   t
   38   1  1250 1300  -   0.7   t
   39   1  1350 1400  +   1.0   F

После этого я хотел переместить все строки, которые в столбце chk имеют "t", в новый df. К сожалению, у меня есть проблема, потому что последнее число последовательностей не включено в это. У кого-нибудь есть идеи как это решить?

Ответы [ 2 ]

2 голосов
/ 13 марта 2019

Мы можем создавать группы для каждого изменения в последовательности, используя diff и выбирать только первую строку из каждой группы, если в группе более 1 строки, и обновлять значение stop до последнего значения в группе.

library(dplyr)

df %>%
   group_by(group = cumsum(c(1, diff(nr) != 1))) %>%
   mutate(stop = last(stop)) %>%
   filter(n() > 1 & row_number() == 1) %>%
   ungroup() %>%
   select(-group)

#     nr   grp start  stop l1    ratio
#  <int> <int> <int> <int> <fct> <dbl>
#1    11     1   300   650 +         1
#2    36     1  1000  1400 +         0
1 голос
/ 13 марта 2019

Легко с data.table:

DT <- fread("   nr  grp start stop l1 ratio
            11   1   300  350  +   1.0                  
            12   1   400  450  -   0.8                  
            13   1    50  550  +   1.0                  
            14   1   600  650  -   1.0                  
            21   1   800  850  -   1.0                  
            36   1  1000 1050  +   0.0       
            37   1  1100 1200  +   0.9
            38   1  1250 1300  -   0.7
            39   1  1350 1400  +   1.0")

setDT(DT) #if you haven't imported with fread

#create group ID, here for didactic reason
DT[, groups := cumsum(c(TRUE, diff(nr) != 1))]

#take first row and replace stop from last row
DT[, if (.N > 1) {
  res <- .SD[1]
  res$stop <- .SD[.N, stop]
  res
  } else NULL, by = groups]
#   groups nr grp start stop l1 ratio
#1:      1 11   1   300  650  +     1
#2:      3 36   1  1000 1400  +     0
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...