data.table中的每一行,我需要从向量中找到最接近的较低数字。以下最小工作示例完成了这项工作,但速度太慢,特别是对于较长的pre.numbers向量(实际数据中约有100万个元素)。
library(data.table)
set.seed(2)
pre.numbers <- sort(floor(runif(50000, 1, 1000000)))
the.table <- data.table(cbind(rowid=1:10000, current.number=floor(runif(1000, 1, 100000)), closest.lower.number=NA_integer_))
setkey(the.table, rowid)
the.table[, closest.lower.number:=max(pre.numbers[pre.numbers<current.number]), by=rowid]
必须有一种更聪明的方法来做到这一点。 vector-number与data.table中的数字之间没有关系。
答案 0 :(得分:4)
这个怎么样?使用data.table的滚动连接:
DT = data.table(pre = pre.numbers,
current.number = pre.numbers+0.5, key="current.number")
setkey(the.table, current.number)
ans = DT[the.table, roll=Inf, rollends=FALSE]
由于你正在处理整数,我刚刚添加了0.5(0到1之间的任何数字应该没问题)从DT
创建pre.numbers
。
最后一步执行 LOCF滚动连接(最后一次观察结果)。对于current.number
(键列)的每个值,在DT
的{{1}}(键列)中查找匹配的行。如果没有匹配,则向前滚动最后一个观察。如果匹配发生在开头/结尾,则会产生current.number
(NA
)。
为了更好地说明发生的情况,请考虑以下情况:
rollends = FALSE
我们首先将pre.numbers转换为# pre.numbers:
# c(10, 11)
# the.table:
# current.numbers
# 9
# 10
# 11
,这将产生列
DT
对于# DT:
# pre current.numbers (key col)
# 10 10.5
# 11 11.5
中的每个值:
the.table
HTH
以下是我用来生成数据的代码:
# 9 -> falls before 10.5, LOCF and rollends = FALSE => result is NA
# 10 -> falls before 10.5 => same as above
# 11 -> falls between 10.5 and 11.5, LOCF matches with previous row = 10.5
# corresponding pre = 10.