r-如何检查tibble中不同行之间的组合或匹配



我有一个像这样的大文件:

library(tidyverse)
test <- structure(list(one = c(5014, 5014, 5014, 5033, 5033, 5033, 5040, 
5040, 5040, 5171, 5171, 5171, 5174, 5174, 5174, 5183, 5183, 5183, 
5193, 5193, 5193, 5304, 5304, 5304), two = c(5033, 5040, 5304, 
5014, 5040, 5304, 5014, 5033, 5304, 5174, 5183, 5331, 5171, 5183, 
5331, 5171, 5174, 5331, 5161, 1538, 5190, 5014, 5033, 5040)), row.names = c(NA, 
-24L), class = c("tbl_df", "tbl", "data.frame"))

两列中的数字以(递归?)方式与其他数字匹配(对不起,我不知道如何更好地解释它)。在这个示例中,很明显(对于人类,而不是计算机)只有三组。如何将这些组分开?

我只需要这样的东西:

组号
1 5014
15033
15040
15304
25171
25183
25331
35193
35161
11538
3 5190

我想多个自联接是可能的,但这似乎非常乏味。。。

使用igraph:

library(igraph)
graph_from_data_frame(test) |>
components() |>
getElement("membership") |>
stack() |>
arrange(values)

输出

values  ind
1       1 5014
2       1 5033
3       1 5040
4       1 5304
5       2 5171
6       2 5174
7       2 5183
8       2 5331
9       3 5193
10      3 5161
11      3 1538
12      3 5190

这有点复杂,但它可以工作:

library(tidyverse)
test |> 
group_by(one) |> 
mutate(n = cur_group_id()) |>
unite("z", one:two, na.rm = TRUE, remove = T) |> 
separate_rows(z) |> 
distinct(z,.keep_all = T) |> 
group_by(n) |> 
mutate(n = cur_group_id())
#> # A tibble: 12 × 2
#> # Groups:   n [3]
#>    z         n
#>    <chr> <int>
#>  1 5014      1
#>  2 5033      1
#>  3 5040      1
#>  4 5304      1
#>  5 5171      2
#>  6 5174      2
#>  7 5183      2
#>  8 5331      2
#>  9 5193      3
#> 10 5161      3
#> 11 1538      3
#> 12 5190      3

在您的评论后添加

问题是dplyr中的一些函数可能被其他包中的函数屏蔽。克服这个问题的一种方法是在函数名称之前使用dplyr::,如:dplyr::mutate(n = dplyr::cur_group_id())

另一种选择是分离tidyverse,只加载所需的包,这里是dplyrtidy。这就是我在这种情况下所做的。您可以看到该代码适用于两个测试DF。

library(dplyr)
library(tidyr)
test2 <- structure(list(one = c(7600, 7606, 7600, 7600, 7600, 8224, 8224, 8228), two = c(1142, 1142, 1162, 1174, 1186, 4942, 4952, 4952)), row.names = c(NA, -8L), class = c("tbl_df", "tbl", "data.frame"))
test2 |>
group_by(one) |>
mutate(n = cur_group_id()) |>
unite("z", one:two, na.rm = TRUE, remove = T) |>
separate_rows(z) |>
distinct(z, .keep_all = T) |>
group_by(n) |>
mutate(n = dplyr::cur_group_id())
#> # A tibble: 10 × 2
#> # Groups:   n [4]
#>    z         n
#>    <chr> <int>
#>  1 7600      1
#>  2 1142      1
#>  3 7606      2
#>  4 1162      1
#>  5 1174      1
#>  6 1186      1
#>  7 8224      3
#>  8 4942      3
#>  9 4952      3
#> 10 8228      4

最新更新