【发布时间】:2017-11-05 17:21:34
【问题描述】:
我有两个数据框。数据框 A 有许多观察/行、每个观察的 ID 以及许多附加列。对于观测值 X 的子集,一组列的值缺失/NA。数据框 B 包含 X 中的观察子集(可以使用 ID 跨数据框进行匹配)和与数据框 A 中名称相同的变量,但包含用缺失值替换列集中缺失值的值/不。
我下面的代码(使用连接操作)只是添加列而不是替换缺失值。对于 B 中的每个附加变量(我们将它们命名为 W),结果表会生成 W.x 和 W.y。
library(dplyr)
foo <- data.frame(id = seq(1:6), x = c(NA, NA, NA, 1, 3, 8), z = seq_along(10:15))
bar <- data.frame(id = seq(1:2), x = c(10, 9))
dplyr::left_join(x = foo, y = bar, by = "id")
我正在尝试使用基于 ID 的 B 中的值替换 A 中的缺失值,但由于我有很多列和很多行,所以这样做很有效。我的目标是:
id x z
1 1 10 1
2 2 9 2
3 3 NA 3
4 4 1 4
5 5 3 5
6 6 8 6
一个想法是在加入后使用 ifelse(),但是为所有变量键入 ifelse() 函数是不可行的。有没有办法在没有数据库连接的情况下简单地做到这一点,或者有没有办法在所有以 .x 结尾的列上应用一个函数,如果 .x 中的值丢失,则用 .y 中的值替换 .x 中的值?
【问题讨论】:
-
这是“更新加入”问题,我还没有看到一个很好的答案。目前我已经转到
left_join(foo, bar, by = 'id') %>% mutate(x = coalesce(x.x, x.y)) %>% select(-contains('.')) -
似乎应该有一种方法可以避免为每个变量手动输入 mutate(foo = coalesce(foo.x, foo.y)) 因为我有成千上万个变量。我一直在考虑使用
apply的方法,但有点不知所措。 -
在
data.table-foo[bar,on=.(id),x := i.x] -
@user3614648 有一种对列名进行编程的方法,但坦率地说,它并不简单或漂亮。
-
nm <- c("x"); foo[bar,on=.(id), (nm) := mget(paste0("i.",nm))]或类似名称,如果您只想引用名称一次。nm也可以使用names(foo)[c(-1,-length(foo))]定义,以避免输入所有内容。
标签: r database merge data-manipulation