Dplyr对分组中的值应用计算,将每个项目与组中的所有其他项目进行比较

Dplyr对分组中的值应用计算,将每个项目与组中的所有其他项目进行比较,r,dataframe,dplyr,lapply,R,Dataframe,Dplyr,Lapply,我想计算分组中的值是否与分组中的其他值足够不同。具体来说,我想计算出同一个学生在同一天的一节课的结束时间是否与另一节课的开始时间相匹配。使用菱形,这是等效代码: library(ggplot2) diamonds %>% group_by(color, cut) %>% mutate(clash = sum( lapply( diamonds %>% filter(color == color

我想计算分组中的值是否与分组中的其他值足够不同。具体来说,我想计算出同一个学生在同一天的一节课的结束时间是否与另一节课的开始时间相匹配。使用菱形,这是等效代码:

library(ggplot2)
diamonds %>% group_by(color, cut) %>% 
  mutate(clash = sum(
           lapply(
             diamonds %>% 
               filter(color == color, cut == cut, carat != carat) %$% carat,
             function(x) ifelse(x < carat - 0.01 && x > carat + 0.01, 1, 0)))) %>%
  arrange(color, cut, clash)

这使得对diamond的第二次调用看起来不可靠

您可以使用
pmap
来代替
lappy
,它更适合
tidyverse

library(tidyverse)

myfun <- function(.color, .cut, .carat){
 diamonds %>%
    filter(color == .color, cut == .cut, !between(carat, .carat - 0.01, .carat + 0.01)) %>%
    nrow()
}

diamonds %>% 
  mutate(clash = pmap_int(list(color, cut, carat), myfun)) %>%
  arrange(color, cut, clash)

# A tibble: 53,940 x 11
   carat cut   color clarity depth table price     x     y     z clash
   <dbl> <ord> <ord> <ord>   <dbl> <dbl> <int> <dbl> <dbl> <dbl> <int>
 1  1.01 Fair  D     SI2      64.6    56  3003  6.31  6.24  4.05   124
 2  1.01 Fair  D     SI2      64.7    57  3871  6.31  6.27  4.07   124
 3  1.01 Fair  D     SI1      66.3    55  4118  6.22  6.17  4.11   124
 4  1.01 Fair  D     SI2      65.3    55  4205  6.33  6.19  4.09   124
 5  1.01 Fair  D     SI1      65.9    60  4276  6.32  6.18  4.12   124
 6  1.01 Fair  D     SI2      64.6    62  4538  6.26  6.21  4.03   124
 7  1.01 Fair  D     SI1      63.5    58  4751  6.35  6.25  4      124
 8  1.01 Fair  D     SI1      64.6    60  4751  6.12  6.08  3.94   124
 9  1.01 Fair  D     SI1      66.9    54  4751  6.25  6.21  4.17   124
10  1.01 Fair  D     SI1      66.2    56  5122  6.05  6.1   4.02   124

参数名称的点符号是什么?即。carat@pluke这只是为了方便区分列
carat
和特定值
.carat
。您还可以调用变量
carat2
x
。但是我认为如果你把它命名为
carat
并使用
filter(carat==carat,…)
Hmm,你会得到一个错误,不确定这是否有效。为了更容易追踪,我在分组函数中添加了透明度:钻石%>%count(颜色、切割、透明度、克拉)。要返回4个项目,我们可以运行输出%>%过滤器(颜色==“D”,剪切==“公平”,清晰度==“I1”)。结果表明,克拉1.5碰撞了一次,而它根本不应该碰撞。为了修复调整mutate(clash=(pmap_int(list(color,cut,clearity,carat),myfun2)-1))Hm,老实说,我并不真正理解代码背后的应用程序。我只是想把你的代码翻译成
purrr
符号。我可能忽略了这个细节,但很高兴看到有一个简单的解决办法:)@pluke我编辑了我的答案。结果表明,结果实际上是三,而不是零,也不是一。也许我误解了,你想摆脱
就在中间?
library(tidyverse)

myfun <- function(.color, .cut, .carat){
 diamonds %>%
    filter(color == .color, cut == .cut, !between(carat, .carat - 0.01, .carat + 0.01)) %>%
    nrow()
}

diamonds %>% 
  mutate(clash = pmap_int(list(color, cut, carat), myfun)) %>%
  arrange(color, cut, clash)

# A tibble: 53,940 x 11
   carat cut   color clarity depth table price     x     y     z clash
   <dbl> <ord> <ord> <ord>   <dbl> <dbl> <int> <dbl> <dbl> <dbl> <int>
 1  1.01 Fair  D     SI2      64.6    56  3003  6.31  6.24  4.05   124
 2  1.01 Fair  D     SI2      64.7    57  3871  6.31  6.27  4.07   124
 3  1.01 Fair  D     SI1      66.3    55  4118  6.22  6.17  4.11   124
 4  1.01 Fair  D     SI2      65.3    55  4205  6.33  6.19  4.09   124
 5  1.01 Fair  D     SI1      65.9    60  4276  6.32  6.18  4.12   124
 6  1.01 Fair  D     SI2      64.6    62  4538  6.26  6.21  4.03   124
 7  1.01 Fair  D     SI1      63.5    58  4751  6.35  6.25  4      124
 8  1.01 Fair  D     SI1      64.6    60  4751  6.12  6.08  3.94   124
 9  1.01 Fair  D     SI1      66.9    54  4751  6.25  6.21  4.17   124
10  1.01 Fair  D     SI1      66.2    56  5122  6.05  6.1   4.02   124
diamonds2 <- diamonds %>%
  count(color, carat, cut)

myfun2 <- function(.color, .cut, .carat){
  diamonds2 %>%
    filter(color == .color, cut == .cut, !between(carat, .carat - 0.01, .carat + 0.01)) %>%
    pull(n) %>% sum
}

diamonds2 %>% 
  mutate(clash = pmap_int(list(color, cut, carat), myfun2)) %>%
  left_join(diamonds, ., by = c("color", "carat", "cut")) %>%
  arrange(color, cut, clash)
diamonds3 <- diamonds %>%
  count(color, carat, cut, clarity)


myfun3 <- function(.color, .cut, .carat, .clarity){
  diamonds3 %>%
    filter(color == .color, cut == .cut, clarity == .clarity, 
           !between(carat, .carat - 0.01, .carat + 0.01)) %>%
    pull(n) %>% sum
}

 myfun3(.color = "D", .cut == "Fair", .clarity = "I1", .carat = 1.5)   
[1] 3