在R中基于另一数据表的数值范围近似匹配更新数据表
问题需求
需要基于df_unique的数据更新lws_data,由于df_unique$org_rowid的部分值不存在于lws_data中,需采用近似匹配(类似Excel VLOOKUP的approx.match=TRUE)——对lws_data中的每个V1值,找到df_unique里小于等于该值的最大org_rowid,并匹配对应的event_definition_2。
数据表结构
lws_data(示例前30行)
structure(list(V1 = 1:30), row.names = c(NA, -30L), class = c("data.table", "data.frame"), .internal.selfref = <pointer: 0x000001f900011ef0>)
df_unique(示例前30行)
structure(list(org_rowid = c(1L, 302L, 537L, 749L, 1082L, 1266L, 1728L, 2177L, 2362L, 2998L, 3049L, 3361L, 3366L, 3427L, 3748L, 3781L, 3805L, 4053L, 4667L, 4772L, 4776L, 4807L, 4909L, 5017L, 5544L, 5653L, 5660L, 5666L, 5676L, 5700L), event_definition_2 = c(0, 1, 1, 2, 2, 3, 3, 4, 4, 5, 5, 6, 6, 7, 7, 8, 8, 9, 9, 10, 10, 11, 11, 12, 12, 13, 13, 14, 14, 15)), row.names = c(NA, 30L), class = "data.frame")
解决方案
方法1:基础R实现(用findInterval)
因为df_unique$org_rowid是升序排列的,findInterval可以快速定位每个V1对应的区间位置,进而匹配对应值:
# 确保df_unique的org_rowid是升序(示例数据已满足,若不确定可先执行排序) df_unique <- df_unique[order(df_unique$org_rowid), ] # 给lws_data添加匹配后的event_definition_2列 lws_data$event_definition_2 <- df_unique$event_definition_2[findInterval(lws_data$V1, df_unique$org_rowid)]
方法2:data.table滚动连接(大数据集更高效)
如果处理的是大数据集,用data.table的滚动连接性能更优:
library(data.table) # 将df_unique转换为data.table格式 setDT(df_unique) # 设置键并执行滚动连接,roll=TRUE表示匹配最近的前一个符合条件的值 setkey(df_unique, org_rowid) lws_data <- df_unique[lws_data, on = .(org_rowid = V1), roll = TRUE]
内容的提问来源于stack exchange,提问作者Aravindan Kalai
相关产品推荐
相关产品推荐

