首页 > 解决方案 > R dplyr 将来自一个数据帧的唯一值替换为来自具有不相等行号的其他数据帧的唯一值

问题描述

我想用另一个 df 中的唯一 ID 替换一个 df 中的唯一 ID。假设 df_long 包含每次试验的时间序列数据,而 df_short 仅包含一段时间内的平均值。

  1. 如果我必须在 group_by 中使用 ID 进行分组,如何改变 ID 中的值?
  2. 如果数据框的行号不相等,如何将唯一值列表从唯一(df_long$ID)应用到唯一(df_short$ID)?

你会如何使用 dplyr 做到这一点?

#let's assume this df contains averaged trials 
df_short <- data.frame(ID = rep(1:4,each=9), 
                 Trial= rep(1:3,12),  
                 Session = rep(rep(1:3,each=3),4) ) 

df_long <- data.frame(ID = rep(c(11,13,18,19),each=3*3*3), 
                 Trial= rep(rep(c(1,2,3),each=3),4*3),  
                 Time = rep(1:3,3*4*3),
                 Session = rep(rep(1:3,each=9),4))    

    df_short[1:15,]
       ID Trial Session
    1   1     1       1
    2   1     2       1
    3   1     3       1
    4   1     1       2
    5   1     2       2
    6   1     3       2
    7   1     1       3
    8   1     2       3
    9   1     3       3
    10  2     1       1
    11  2     2       1
    12  2     3       1
    13  2     1       2
    14  2     2       2
    15  2     3       2

df_long[1:15,]
   ID Trial Time Session
1  11     1    1       1
2  11     1    2       1
3  11     1    3       1
4  11     2    1       1
5  11     2    2       1
6  11     2    3       1
7  11     3    1       1
8  11     3    2       1
9  11     3    3       1
10 11     1    1       2
11 11     1    2       2
12 11     1    3       2
13 11     2    1       2
14 11     2    2       2
15 11     2    3       2

结果

 ID Trial Session
1  11     1       1
2  11     2       1
3  11     3       1
4  11     1       2
5  11     2       2
6  11     3       2
7  11     1       3
8  11     2       3
9  11     3       3
10 13     1       1
11 13     2       1
12 13     3       1
13 13     1       2
14 13     2       2
15 13     3       2

标签: rdplyr

解决方案


如果要“分别”(按发生顺序)进行替换,这里有两个选项。在这两种情况下,我都将创建一个新列,以便验证结果——我将删除旧列并将新列重命名给您。

# Option 1: with factor conversion
df_short %>%
  mutate(
    new_ID = factor(ID, levels = unique(ID), labels = unique(df_long$ID)),
    new_ID = as.numeric(as.character(new_ID)) # convert to numeric
)

# Option 2: make a look-up table and join
id_lookup = tibble(ID = unique(df_short$ID), new_ID = unique(df_long$ID))
df_short %>% left_join(id_lookup, by = "ID")

如果您的数据按 ID 列分组,则在执行这些操作之前ungroup(),您应该应用这些功能,并group_by()在必要时再次应用。(该连接适用于分组数据,但如果数据已分组,您将无法删除旧的 ID 列。)


推荐阅读