我有两个数据框:
as1 <- data.frame(ID = c(1,2,3,4,5,6),
pID = c(21,22,23,24,25,26),
Values = c(435,33,45,NA, NA,12))
as2 <- data.frame(ID = c(4,5),
pid = c(24,25),
Values = c(544, 676))
Run Code Online (Sandbox Code Playgroud)
我需要通过匹配ID和pID将as1中的NA值替换为as2中的NA值
我需要获取结果数据框架为:
resultdf
ID pID Values
1 1 21 435
2 2 22 33
3 3 23 45
4 4 24 544
5 5 25 676
6 6 26 12
Run Code Online (Sandbox Code Playgroud)
我尝试先做子集,然后na.omit()再执行rbind...但是我丢失了索引。
或者另一个选择是data.table
library(data.table)
setDT(as1)[as2, Values := i.Values , on =.(ID, pid)]
as1
# ID pid Values
#1: 1 21 435
#2: 2 22 33
#3: 3 23 45
#4: 4 24 544
#5: 5 25 676
#6: 6 26 12
Run Code Online (Sandbox Code Playgroud)
用dplyr图书馆试试。首先连接两个表,然后用值而不是创建新列NA:
library("dplyr")
as1 <- data.frame(ID = c(1,2,3,4,5,6), pid = c(21,22,23,24,25,26),Values = c(435,33,45,NA, NA,12))
as2 <- data.frame(ID = c(4,5),pid = c(24,25), Values = c(544, 676))
left_join(as1, as2, by = c("ID", "pid")) %>%
mutate(Values = ifelse(is.na(Values.x), Values.y, Values.x)) %>%
select(ID, pid, Values)
# ID pid Values
# 1 1 21 435
# 2 2 22 33
# 3 3 23 45
# 4 4 24 544
# 5 5 25 676
# 6 6 26 12
Run Code Online (Sandbox Code Playgroud)
这是两个基本的R解决方案。
首先,使用match“ ID”中的as1选择“值”的元素以填写:
as1$Values[match(as2$ID, as1$ID)] <- as2$Values
as1
ID pID Values
1 1 21 435
2 2 22 33
3 3 23 45
4 4 24 544
5 5 25 676
6 6 26 12
Run Code Online (Sandbox Code Playgroud)
仅当ID是两个数据集的真实ID时才有效(即pid是“无关”)。其次,在还需要pid的情况下,可以如下使用merge并“折叠”两个值列:
df <- merge(as1, as2, by.x=c("ID", "pID"), by.y=c("ID", "pid"), all=TRUE)
Run Code Online (Sandbox Code Playgroud)
这将产生一个具有两个值列的四列数据帧。使用以下命令将这些折叠到单个列中ifelse:
df <- cbind(df[c(1,2)], "Values"=with(df, ifelse(is.na(Values.y), Values.x, Values.y)))
df
ID pID Values
1 1 21 435
2 2 22 33
3 3 23 45
4 4 24 544
5 5 25 676
6 6 26 12
Run Code Online (Sandbox Code Playgroud)
按照 Marta 的dplyr解决方案,我们可以使用coalesce代替合并合并的Value.x和Value.y:
library(dplyr)
res <- as1 %>% left_join(as2, by = c("ID", "pID"="pid")) %>%
mutate(Values=coalesce(Values.x,Values.y)) %>%
select(-Values.x,-Values.y)
## ID pID Values
##1 1 21 435
##2 2 22 33
##3 3 23 45
##4 4 24 544
##5 5 25 676
##6 6 26 12
Run Code Online (Sandbox Code Playgroud)
还要注意用于by参数的语法left_join。在这里,我们ID通过pIDforas1和pidfor加入as2。
| 归档时间: |
|
| 查看次数: |
6550 次 |
| 最近记录: |