You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

按分组与最邻近年份值合并DataFrame(tidyverse实现)

解决方案

1. 基础实现:匹配任意最邻近年份

你的问题出在分组维度不对——得按color加df1的每一行(也就是color, year.x)分组,而不是只按color分组,这样才能给df1的每条观测单独找对应组内最接近的df2记录。

用tidyverse的代码实现如下:

library(tidyverse)

# 先把data.table转成tibble(tidyverse更适配,也可以直接用data.table操作,这里按你要求用tidyverse)
df1 <- as_tibble(df1)
df2 <- as_tibble(df2)

df3 <- df1 %>%
  left_join(df2, by = "color", suffix = c(".x", ".y")) %>%
  group_by(color, year.x) %>%  # 按color+df1的年份分组,保证每条df1记录单独处理
  mutate(year_diff = abs(year.x - year.y)) %>%
  filter(year_diff == min(year_diff)) %>%
  select(color, year = year.x, value) %>%
  ungroup()

df3

运行后会得到你想要的结果:

# A tibble: 4 × 3
  color  year value
  <chr> <dbl> <int>
1 Green  1995     1
2 Green  2001     2
3 Red    2010     3
4 Red    1997     3

2. 指定匹配方向:前/后邻近年份

如果需要指定匹配之前最近的年份(df2年份≤df1年份)或之后最近的年份(df2年份≥df1年份),可以修改过滤逻辑:

匹配之后最近的年份(df2年份不早于df1)

df3_after <- df1 %>%
  left_join(df2, by = "color", suffix = c(".x", ".y")) %>%
  group_by(color, year.x) %>%
  filter(year.y >= year.x) %>%  # 只保留df2中年份晚于/等于df1的记录
  mutate(year_diff = year.y - year.x) %>%
  filter(year_diff == min(year_diff)) %>%
  select(color, year = year.x, value) %>%
  ungroup()

匹配之前最近的年份(df2年份不晚于df1)

df3_before <- df1 %>%
  left_join(df2, by = "color", suffix = c(".x", ".y")) %>%
  group_by(color, year.x) %>%
  filter(year.y <= year.x) %>%  # 只保留df2中年份早于/等于df1的记录
  mutate(year_diff = year.x - year.y) %>%
  filter(year_diff == min(year_diff)) %>%
  select(color, year = year.x, value) %>%
  ungroup()

3. 补充说明

  • 用left_join而非inner_join,确保df1的所有观测都能保留(如果某组df2没有对应记录,value会显示为NA)
  • 如果df2同组内有多个年份和df1年份差值相同(比如同时存在前后等距的年份),上面的代码会保留所有匹配项;要是只想留一个,可以再加slice_head(n=1)这类逻辑筛选

内容的提问来源于stack exchange,提问作者flâneur

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.04 01:35:16