识别布尔值序列中连续TRUE段的最后一个元素位置
问题:用Base R优雅识别TRUE/FALSE向量中切换为FALSE前的最后一个TRUE位置
我有一个由TRUE和FALSE组成的向量:
x <- c(F,F,F,T,T,T,F,F,F,T,T,T,F,T,T)。我希望用Base R优雅地识别出每个切换为FALSE之前的最后一个TRUE的位置。以下代码可实现需求,但似乎可简化:c((x[-1] != x[-length(x)]),T) & x > FALSE,其输出为:FALSE FALSE FALSE FALSE FALSE TRUE FALSE FALSE FALSE FALSE FALSE TRUE FALSE FALSE TRUE。
你的思路没问题,但确实能简化得更优雅!这里有个Base R的简洁写法,逻辑更直观,代码也更短:
x <- c(F,F,F,T,T,T,F,F,F,T,T,T,F,T,T) diff(c(x, FALSE)) < 0
运行结果和你原代码完全一致:
[1] FALSE FALSE FALSE FALSE FALSE TRUE FALSE FALSE FALSE FALSE FALSE TRUE FALSE FALSE TRUE
为什么这个写法更优?
- 逻辑直接戳点:我们要找的是「连续TRUE段的最后一个元素」,本质就是「从TRUE切换到FALSE」的前一个位置。给
x末尾补一个FALSE,就能让原向量末尾的TRUE段也触发这个切换逻辑。 - 巧用diff特性:R里逻辑值会自动转成数值(TRUE=1,FALSE=0),
diff()计算相邻元素的差值。当从TRUE(1)切到FALSE(0)时,差值是0-1=-1,也就是小于0,正好对应我们要的位置。 - 无冗余操作:不用像原代码那样截断向量首尾,也不需要额外的
& x > FALSE条件,一步到位搞定。
如果想贴近你原代码的逻辑调整,也可以写成:
x & c(tail(x, -1) != head(x, -1), TRUE)
但显然diff(c(x, FALSE)) < 0是最简洁直观的版本。
内容的提问来源于stack exchange,提问作者Khaynes
相关产品推荐
相关产品推荐

