识别匹配对并创建一个公共密钥
Identify matched pairs and create a common key
我有
df<-data.frame(record_id=c("A", "B", "C", "D", "E", "F"), var1=1:6, matched.with=rev(c("A", "B", "C", "D", "E", "F")))
> df
record_id var1 matched.with
1 A 1 F
2 B 2 E
3 C 3 D
4 D 4 C
5 E 5 B
6 F 6 A
因此,id A
已与 F
、B
与 E
、C
与 D
[=25= 匹配]
我想为
这样的对创建一个 common.key
变量
df.common.key
record_id var1 matched.with common.key
1 A 1 F 1
2 B 2 E 2
3 C 3 D 3
4 D 4 C 3
5 E 5 B 2
6 F 6 A 1
这表明 A
已与 F
(第 1 行)的键 1
匹配,F
已与 A
(第 1 行)匹配6) 还有键 1
。 Common key不一定是数字,也可以是string或factor。
我如何完成此操作 1) 如果我的数据框包含 仅 匹配对,2) 如果我的 DF 还包含观察结果 而没有 配对 3) 是否有 tidyverse 解决方案?
您可以使用一个临时变量来完成此操作,该变量按字母顺序粘贴 record_id
和 matched.with
中的字符串 (row-wise),然后按该变量分组并选择第一个 var1
放入 common.key
df %>%
rowwise() %>%
mutate(common = paste0(sort(c(record_id, matched.with)), collapse = '')) %>%
group_by(common) %>%
mutate(common.key = first(var1)) %>%
ungroup() %>%
select(-common)
#> # A tibble: 6 x 4
#> record_id var1 matched.with common.key
#> <chr> <int> <chr> <int>
#> 1 A 1 F 1
#> 2 B 2 E 2
#> 3 C 3 D 3
#> 4 D 4 C 3
#> 5 E 5 B 2
#> 6 F 6 A 1
加入:
library(tidyverse)
df %>%
mutate(id = pmin(matched.with, record_id)) %>%
left_join(select(df, record_id, var1), by = c("id" = "record_id")) %>%
select(record_id, var1 = var1.x, matched.with, common.key = var1.y)
# A tibble: 6 x 4
record_id var1 matched.with common.key
<chr> <int> <chr> <int>
1 A 1 F 1
2 B 2 E 2
3 C 3 D 3
4 D 4 C 3
5 E 5 B 2
6 F 6 A 1
我们可以使用pmin
和pmax
得到唯一的字母组合(顺序相同)。然后,我们可以使用 grp
列来创建 common.key
.
library(tidyverse)
df %>%
group_by(grp = paste0(pmin(record_id, matched.with), pmax(record_id, matched.with))) %>%
mutate(common.key = cur_group_id()) %>%
select(-grp)
输出
grp record_id var1 matched.with common.key
<chr> <chr> <int> <chr> <int>
1 AF A 1 F 1
2 BE B 2 E 2
3 CD C 3 D 3
4 CD D 4 C 3
5 BE E 5 B 2
6 AF F 6 A 1
我们也可以使用
library(dplyr)
library(stringr)
df %>%
group_by(grp = str_c(pmin(record_id, matched.with),
pmax(record_id, matched.with))) %>%
mutate(common.key = first(var1)) %>%
ungroup %>%
select(-grp)
-输出
# A tibble: 6 × 4
record_id var1 matched.with common.key
<chr> <int> <chr> <int>
1 A 1 F 1
2 B 2 E 2
3 C 3 D 3
4 D 4 C 3
5 E 5 B 2
6 F 6 A 1
我有
df<-data.frame(record_id=c("A", "B", "C", "D", "E", "F"), var1=1:6, matched.with=rev(c("A", "B", "C", "D", "E", "F")))
> df
record_id var1 matched.with
1 A 1 F
2 B 2 E
3 C 3 D
4 D 4 C
5 E 5 B
6 F 6 A
因此,id A
已与 F
、B
与 E
、C
与 D
[=25= 匹配]
我想为
这样的对创建一个common.key
变量
df.common.key
record_id var1 matched.with common.key
1 A 1 F 1
2 B 2 E 2
3 C 3 D 3
4 D 4 C 3
5 E 5 B 2
6 F 6 A 1
这表明 A
已与 F
(第 1 行)的键 1
匹配,F
已与 A
(第 1 行)匹配6) 还有键 1
。 Common key不一定是数字,也可以是string或factor。
我如何完成此操作 1) 如果我的数据框包含 仅 匹配对,2) 如果我的 DF 还包含观察结果 而没有 配对 3) 是否有 tidyverse 解决方案?
您可以使用一个临时变量来完成此操作,该变量按字母顺序粘贴 record_id
和 matched.with
中的字符串 (row-wise),然后按该变量分组并选择第一个 var1
放入 common.key
df %>%
rowwise() %>%
mutate(common = paste0(sort(c(record_id, matched.with)), collapse = '')) %>%
group_by(common) %>%
mutate(common.key = first(var1)) %>%
ungroup() %>%
select(-common)
#> # A tibble: 6 x 4
#> record_id var1 matched.with common.key
#> <chr> <int> <chr> <int>
#> 1 A 1 F 1
#> 2 B 2 E 2
#> 3 C 3 D 3
#> 4 D 4 C 3
#> 5 E 5 B 2
#> 6 F 6 A 1
加入:
library(tidyverse)
df %>%
mutate(id = pmin(matched.with, record_id)) %>%
left_join(select(df, record_id, var1), by = c("id" = "record_id")) %>%
select(record_id, var1 = var1.x, matched.with, common.key = var1.y)
# A tibble: 6 x 4
record_id var1 matched.with common.key
<chr> <int> <chr> <int>
1 A 1 F 1
2 B 2 E 2
3 C 3 D 3
4 D 4 C 3
5 E 5 B 2
6 F 6 A 1
我们可以使用pmin
和pmax
得到唯一的字母组合(顺序相同)。然后,我们可以使用 grp
列来创建 common.key
.
library(tidyverse)
df %>%
group_by(grp = paste0(pmin(record_id, matched.with), pmax(record_id, matched.with))) %>%
mutate(common.key = cur_group_id()) %>%
select(-grp)
输出
grp record_id var1 matched.with common.key
<chr> <chr> <int> <chr> <int>
1 AF A 1 F 1
2 BE B 2 E 2
3 CD C 3 D 3
4 CD D 4 C 3
5 BE E 5 B 2
6 AF F 6 A 1
我们也可以使用
library(dplyr)
library(stringr)
df %>%
group_by(grp = str_c(pmin(record_id, matched.with),
pmax(record_id, matched.with))) %>%
mutate(common.key = first(var1)) %>%
ungroup %>%
select(-grp)
-输出
# A tibble: 6 × 4
record_id var1 matched.with common.key
<chr> <int> <chr> <int>
1 A 1 F 1
2 B 2 E 2
3 C 3 D 3
4 D 4 C 3
5 E 5 B 2
6 F 6 A 1