我有一个充满名称的数据框。
对于数据框中的给定行,我想将该行与df中该行上方的每一行进行比较,并确定每一行的匹配名称数是否小于或等于4。
玩具示例,其中第3行是感兴趣的行
“ Jim”,“ Dwight”,“ Michael”,“ Andy”,“ Stanley”,“ Creed”
“ Jim”,“ Dwight”,“ Angela”,“ Pam”,“ Ryan”,“ Jan”
“ Jim”,“ Dwight”,“ Angela”,“ Pam”,“ Creed”,“ Ryan”
因此,我们首先将第3行与第1行进行比较,然后看到名称重叠为3,这符合<= 4个条件。
然后,我们将第3行与第2行进行比较,发现名称重叠为5,这不符合<= 4的条件,最终返回失败条件,条件是上面的每一行都为<= 4。
现在,我正在使用for循环执行此操作,但是对于我正在使用的数据帧大小,速度太慢了。
较早的答案创建了一个以列类型为因素的结构。大概的目的不是比较因素而是比较字符值。您可以通过天真地尝试用以下方法交换该结构的第一行中前两个项目的值来查看这种混乱的根源:
df[1,2:1] <- df[1,1:2] # results in NA's in those positions rather than a value swap
这里是一组字符值的列,将允许字符到字符的比较。
df2 <- structure(list(V1 = c("Jim", "Jim", "Jim"), V2 = c("Dwight", "Dwight", "Dwight"), V3 = c("Michael", "Angela", "Angela"), V4 = c("Andy", "Pam", "Pam"), V5 = c("Stanley", "Ryan", "Creed"), V6 = c("Creed", "Jan", "Ryan")), class = "data.frame", row.names = c(NA, -3L))
要使用%in%进行基于行的比较,您需要使用
apply
(这会导致逻辑值的转置集(暴露出R的apply结果的古怪之处),并且意味着您需要沿着列对匹配进行计数:
apply(df2, 1, function(x) x %in% df2[3,])
[,1] [,2] [,3]
[1,] TRUE TRUE TRUE
[2,] TRUE TRUE TRUE
[3,] FALSE TRUE TRUE
[4,] FALSE TRUE TRUE
[5,] FALSE TRUE TRUE
[6,] TRUE FALSE TRUE
> colSums( apply(df2, 1, function(x) x %in% df2[3,]) ) <= 4
[1] TRUE FALSE FALSE
示例数据