【发布时间】:2018-04-19 09:16:17
【问题描述】:
library(tidyverse)
我有两个名为 Df1 和 Df2 的数据帧(参见底部的示例代码)。我想在 Df1 中(从所有列中)查找不在 Df2 中的任何电话号码列中的电话号码。
首先,我重组 Df1 以便每行只有一个 Id。
Df1<-Df1 %>%
gather(key, value, -Id) %>%
filter(!is.na(value)) %>%
select(-key) %>%
group_by(Id) %>%
filter(!duplicated(value)) %>%
mutate(Phone=paste0("Phone_",1:n())) %>%
spread(Phone, value)
接下来,我重命名 Df2,然后使用连接仅在 Df1 中查找 Df2 中的 Id。
Df2<-Df2%>%set_names(c("Id","Ph1","Ph2"))
DfJoin<-left_join(Df2,Df1,by="Id")
这就是我卡住的地方。我想找到 Df1(Phone1 Phone2 和 Phone 3)中所有不在 Df2(Ph1 和 Ph2)中的号码。下面是一些关于代码的想法。我尝试了这个想法的许多变体,但找不到实现我想要的方法。最终产品应该只是一个表格,其中包含不在任何 Df2 列中的任何 Df1 列中的电话号码以及关联的 Id。我还想知道是否还有其他联接或设置操作可以更有效地实现这一目标?
DfJoin<-DfJoin%>%mutate(New=if_else(! DfJoin[2:3] %in% DfJoin[4:6]),1,0)
DfJoin<-DfJoin%>%filter(! DfJoin[2:3] %in% DfJoin[2:4])
样本数据:
数据框 1:
Id<-c(199,148,148,145,177,165,144,121,188,188,188,111)
Ph1<-c(6532881717,6572231223,6541132112,6457886543,6548887777,7372222222,6451123425,6783450101,7890986543,6785554444,8764443344,6453348736)
Ph2<-c(NA,NA,NA,NA,NA,7372222222,NA,NA,NA,6785554444,NA,NA)
Df1<-data.frame(Id,Ph1,Ph2)
数据框 2:
Id2<-c(199,148,142,145,177,165,144,121,182,109,188,111)
Phone1<-c(6532881717,6572231223,6541132112,6457886543,6548887777,7372222222,6451123425,6783450101,7890986543,6785554400,8764443344,6453348736)
Phone2<-c(NA,NA,NA,NA,NA,7372222222,NA,NA,NA,6785554444,NA,NA)
Df2<-data.frame(Id2,Phone1,Phone2)
【问题讨论】:
-
在基础 R 中,您可以使用类似
setdiff(unlist(Df1[("Ph1", "Ph2")]), unlist(Df2[c("Phone1", "Phone2")]))的方式来获取 Df1 中不在 Df1 中的所有电话号码。setdiff删除 NA。