从包含间隙的序列中获取起始和结束范围



假设我有以下数据:

c(1:4,7:15,20:23,25,30:35,40,41)

我想要得到这个向量的起始和结束范围。然而,我想跳过单个值,它没有自然的前驱和后继(在示例中:25)。换句话说,至少要有两个连续的值才能构成一个"范围"。

本例中起始范围为:1, 7, 20, 30, 40它们对应的结束范围为:4, 15, 23, 35, 41

是否有优雅的内置解决方案?我几乎被困在for循环的地狱里了。

确定diff(x)所在位置>1,通过在序列的开头或结尾添加TRUE来适当地滞后。(diff(x)产生一个比x短一个元素的向量。)&子句去掉了单例值。

dx1 <- c(TRUE,diff(x)>1)
dx2 <- c(diff(x)>1, TRUE)
start <- x[dx1 & !dx2]
end <-   x[dx2 & !dx1]

也可能有一个类似rle(diff(x)==1)的解决方案,但它会比上面的解决方案更复杂一些(如果你想要识别特定长度的运行,它可能会有用)。

对@Ben Bolker的解决方案没有多大帮助,但另一种方法可以是:

ind <- aggregate(x ~ cumsum(c(FALSE, diff(x)) > 1), FUN = function(x) (length(x) > 1) * range(x))
ind$x[ind$x[, 1] != 0, ]
[,1] [,2]
[1,]    1    4
[2,]    7   15
[3,]   20   23
[4,]   30   35
[5,]   40   41

最新更新