【问题标题】:R: loop through 2 columns to subset a data.table or data.frameR:遍历 2 列以子集 data.table 或 data.frame
【发布时间】:2021-09-12 16:30:27
【问题描述】:

我想使用循环将 data.table 或数据框按两列进行子集化。我想知道如何使用 purrr 或 dplyr 以一种很好的方式做到这一点。

这是我的例子:

library(data.table)

# my example data
DF <- as.data.table(cbind.data.frame(x = c(100.01, 100.03, 100.09, 100.01, 233.45, 233.56, 233.51, 233.45, 561.1, 556.1, 447.23),
                    y = c(11, 10.8, 10.9, 20, 2, 2.2, 4, 6, 11, 2.1, 10.6)))

# my filter conditions
mycondition <- cbind.data.frame(c1 = c(100, 233.5), c2 = c(11, 2))

## subset DF by selecting the values in mycondition with a tolerance of 0.5
result1 <- DF[x%between%c(mycondition$c1[1] - 0.5, mycondition$c1[1] + 0.5) & y%between%c(mycondition$c2[1] - 0.5, mycondition$c2[1] + 0.5)]

result2 <- DF[x%between%c(mycondition$c1[2] - 0.5, mycondition$c1[2] + 0.5) & y%between%c(mycondition$c2[2] - 0.5, mycondition$c2[2] + 0.5)]

## combined result
result <- rbind.data.frame(result1, result2)

> result
        x    y
1: 100.01 11.0
2: 100.03 10.8
3: 100.09 10.9
4: 233.45  2.0
5: 233.56  2.2

我想知道是否有一种很好的方法可以使用 R 包 purrr 循环它或使用 dolyr 来执行它?

谢谢。

【问题讨论】:

    标签: r loops data.table subset purrr


    【解决方案1】:

    不需要循环,这是一个纯粹的-data.table 方法。

    library(data.table)
    setDT(mycondition)
    mycondition[, c("c1a", "c1b", "c2a", "c2b") := .(c1-0.5, c1+0.5, c2-0.5, c2+0.5)
      ][DF, on=.(c1a<=x, c1b>=x, c2a<=y, c2b>=y)
      ][!is.na(c1), .(x=c1a, y=c2a)]
    #         x     y
    #     <num> <num>
    # 1: 100.01  11.0
    # 2: 100.03  10.8
    # 3: 100.09  10.9
    # 4: 233.45   2.0
    # 5: 233.56   2.2
    

    仅供参考,您生成数据的代码过于复杂。以下是功能等效的:

    DF <- as.data.table(cbind.data.frame(x = c(100.01, 100.03, 100.09, 100.01, 233.45, 233.56, 233.51, 233.45, 561.1, 556.1, 447.23),
                        y = c(11, 10.8, 10.9, 20, 2, 2.2, 4, 6, 11, 2.1, 10.6)))
    DF <- data.table(x = c(100.01, 100.03, 100.09, 100.01, 233.45, 233.56, 233.51, 233.45, 561.1, 556.1, 447.23),
                     y = c(11, 10.8, 10.9, 20, 2, 2.2, 4, 6, 11, 2.1, 10.6))
    
    mycondition <- cbind.data.frame(c1 = c(100, 233.5), c2 = c(11, 2))
    mycondition <- data.frame(c1 = c(100, 233.5), c2 = c(11, 2)) # though not a data.table, as I need above
    mycondition <- data.table(c1 = c(100, 233.5), c2 = c(11, 2))
    

    既然你已经在使用data.table,我建议你停止使用rbind.data.frame,因为它不像rbind.data.table,又名rbind(DF, ...)那样有特色(或者可能安全?)。 data.table::rbindlist(list(result1, result2)) 可能更好,因为它有一些附加功能。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2012-05-22
      • 1970-01-01
      • 1970-01-01
      • 2013-01-08
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多