【问题标题】:R: Efficiently filter numeric vector by selecting multiple subregions [duplicate]R:通过选择多个子区域有效地过滤数值向量[重复]
【发布时间】:2017-06-07 22:35:35
【问题描述】:

我有一个相对较大的数值向量x,我只对在n 子区域中找到的值感兴趣,这些子区域由lowerupper 边界(包括)指定。完成此任务的最有效(最重要)和简洁(只要代码可读就不太重要)的方法是什么?我需要输出是逻辑(或整数)值的向量,以便我可以用选定的区域索引另一个向量。

假设我有以下数据:

x <- 1:20
lower <- c(0.8, 3.9,  9, 12, 19)
upper <- c(2.1, 6.1, 13, 17, 19)

输出应该是:

out <- c(TRUE,  TRUE, FALSE, TRUE, TRUE, TRUE, FALSE, FALSE, TRUE, TRUE, 
         TRUE,  TRUE, TRUE,  TRUE, TRUE, TRUE, TRUE,  FALSE, TRUE, FALSE)

我有一个解决方案,但对我来说似乎有点老套,我不知道它是否有效:

library(dplyr)
library(purrr)

out.list <- map2(lower, upper, ~ between(x, .x, .y))
out.mat <- do.call(rbind, out.list)
out.vec <- apply(out.mat, 2, any)

# Check output
all(out.vec == out)
[1] TRUE

虽然x 预计不会超过一百万个元素,但我需要对许多不同的 x 值重复该过程。

编辑:更新了浮点和重叠边界的示例。

更新:我认为这个问题比链接的问题更简洁和笼统。我会选择已删除的 data.table 答案,而不是链接问题中的选定答案(它偏好 dplyr/tidyr)。

library(data.table)
library(microbenchmark)

lower <- runif(100, 0.5, 8.5)
upper <- runif(100, 0, 1)
x <- runif(1e5, 1, 10)

microbenchmark(inrange = inrange(x, lower, upper),
               sapply = sapply(x,function(v){ any(v >= lower & v <= upper) })) 

   expr        min         lq       mean    median         uq      max neval
inrange   5.757293   5.991459   6.527294   6.10907   6.417622  10.0425   100
 sapply 280.412724 290.914073 300.813885 295.15648 300.568322 356.7478   100

【问题讨论】:

  • 刚开始查找inrange函数时才看到这篇文章。
  • 如果链接的答案正常,我们可以将其作为欺骗关闭
  • @docendodiscimus 没问题,但我更喜欢您发布的 inrange() 解决方案。链接的问题对 dplyr/tidyr 有明确的偏好。

标签: r select vector


【解决方案1】:

这个呢?

out <- sapply(x,function(v){ any(v >= lower & v <= upper) })

> out 
[1]  TRUE  TRUE FALSE  TRUE  TRUE  TRUE FALSE FALSE  TRUE  TRUE  TRUE
[12]  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE FALSE  TRUE FALSE

【讨论】:

    猜你喜欢
    • 2019-09-29
    • 1970-01-01
    • 2018-03-13
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多