无车辆编号时,从公共交通时刻表数据中匹配前序站点对应时间
解决无车辆编号时匹配公共交通前序站点停留时间的问题
我需要处理公共交通时刻表数据,为每条记录找到对应前序站点的、早于当前记录时间的最近时间,但数据中没有vehicle_number字段来区分不同车次。
测试数据如下:
library(tidyverse) data <- tribble( ~stop, ~prev_stop, ~time, 5, 4, 10, 6, 5, 10.1, 7, 6, 10.2, 9, 7, 10.3, 5, 4, 11, 6, 5, 11.1, 7, 6, 11.2, 9, 7, 11.3, 5, 4, 12, 6, 5, 12.1, 7, 6, 12.2, 9, 7, 12.3 )
我尝试的代码逻辑存在语法错误,无法正确运行:
data %>% mutate(time_at_prev_stop = max(time[stop{in another row) == prev_stop{in current row}] & time {in target row}<time{in current row}))
可行解决方案
方法1:使用purrr::map2逐行匹配
这种方法直观易懂,适合小数据集:
data <- data %>% mutate( # 遍历每条记录的prev_stop和time,筛选对应前序站点且时间更早的最大时间 time_at_prev_stop = map2_dbl(prev_stop, time, ~ max(data$time[data$stop == .x & data$time < .y], na.rm = TRUE)) ) %>% # 处理无匹配的情况(比如第一条记录prev_stop=4无对应站点),将-Inf替换为NA mutate(time_at_prev_stop = ifelse(time_at_prev_stop == -Inf, NA, time_at_prev_stop))
运行后结果:
| stop | prev_stop | time | time_at_prev_stop |
|---|---|---|---|
| 5 | 4 | 10 | NA |
| 6 | 5 | 10.1 | 10 |
| 7 | 6 | 10.2 | 10.1 |
| 9 | 7 | 10.3 | 10.2 |
| 5 | 4 | 11 | NA |
| 6 | 5 | 11.1 | 11 |
| 7 | 6 | 11.2 | 11.1 |
| 9 | 7 | 11.3 | 11.2 |
| 5 | 4 | 12 | NA |
| 6 | 5 | 12.1 | 12 |
| 7 | 6 | 12.2 | 12.1 |
| 9 | 7 | 12.3 | 12.2 |
方法2:自连接(适合大数据量)
自连接的效率更高,避免逐行遍历的性能损耗:
# 先构建站点-到达时间的映射表 data_prev <- data %>% select(stop_to_match = stop, prev_time = time) # 自连接匹配前序站点,筛选并保留最近的时间 data <- data %>% left_join(data_prev, by = c("prev_stop" = "stop_to_match")) %>% filter(prev_time < time) %>% group_by(stop, prev_stop, time) %>% slice_max(prev_time, n = 1) %>% ungroup() %>% right_join(data, by = c("stop", "prev_stop", "time")) %>% rename(time_at_prev_stop = prev_time)
原代码问题说明
你尝试的代码存在两处核心问题:
- 错误使用
{}指代其他行,R中需要用向量筛选的方式(如data$stop == .x)定位目标数据 - 逻辑条件的语法错误,
max函数的参数应该是符合筛选条件的时间向量,而非逻辑判断向量
内容的提问来源于stack exchange,提问作者Jonathan Nolan
相关产品推荐
相关产品推荐

