在 R 中,如何根据另一个单元格的值删除一系列单元格?
In R, how to delete a series of cells based on the value from another cell?
我有一个 300x300 的 df。每行代表不同患者的数据,以 id 命名。前两列是患者 ID。列 'id_all' 包含的参与者多于需要,多于 'id'。我的目标是仅保留与第一列 'id'.
相对应的患者信息
第一个 9x9 看起来像这样:
id
id_all
MMSE BL
MMSE 12
MMSE 24
MMSE 36
MMSE 48
MMSE 60
MMSE 72
aaa002
aaa000
22
18
NA
NA
NA
NA
NA
aaa003
aaa002
29
28
28
29
30
29
NA
aaa005
aaa003
30
29
30
30
30
NA
NA
aaa024
aaa005
29
28
25
NA
NA
25
NA
aaa026
aaa024
30
29
29
29
NA
NA
NA
aaa048
aaa026
28
30
28
27
30
30
NA
aaa095
aaa038
29
29
29
26
NA
NA
NA
aaa222
aaa048
30
29
29
28
28
29
NA
因此,基于第一列,我想以某种方式遍历第二列,并删除与第一列不匹配的参与者的所有信息,'id'. 这意味着,在第一行中,删除列 2:300,并保持第一列不变。
最后,我希望我的 df 看起来像这样:
id
id_all
MMSE BL
MMSE 12
MMSE 24
MMSE 36
MMSE 48
MMSE 60
MMSE 72
aaa002
aaa002
29
28
28
29
30
29
NA
aaa003
aaa003
30
29
30
30
30
NA
NA
aaa005
aaa005
29
28
25
NA
NA
25
NA
aaa024
aaa024
30
29
29
29
NA
NA
NA
aaa026
aaa026
28
30
28
27
30
30
NA
aaa048
aaa048
30
29
29
28
28
29
NA
aaa095
...
aaa222
...
在此示例中,id_all aaa000 和 aaa038 在 id 列中没有匹配项,因此我想删除有关这些参与者的所有信息。
我不知道如何删除几乎所有行(几乎是因为只剩下前两个单元格),以及如何将所有单元格向上移动。
另一种可能性是,将第一列向下移动直到 id 匹配 id_all,然后删除 id 列中有空单元格的整行.
谢谢!
在 tidyverse 中:
library(dplyr)
df %>%
filter(id == id_all)
基地内:
df[df$id == df$id_all, ]
我认为这会达到目的
library(tidyverse)
df %>% filter(!is.na(match(id_all, df$id))) %>% select(-id)
id_all MMSE.BL MMSE.12 MMSE.24 MMSE.36 MMSE.48 MMSE.60 MMSE.72
1 aaa002 29 28 28 29 30 29 NA
2 aaa003 30 29 30 30 30 NA NA
3 aaa005 29 28 25 NA NA 25 NA
4 aaa024 30 29 29 29 NA NA NA
5 aaa026 28 30 28 27 30 30 NA
6 aaa048 30 29 29 28 28 29 NA
由于id == id_all
在最终数据中,不需要重复的列。如果需要,可以通过在上述语法
末尾添加mutate(id = id_all)
来轻松创建
df %>% filter(!is.na(match(id_all, df$id))) %>% select(-id) %>% mutate(id = id_all) %>%
select(id, everything())
id id_all MMSE.BL MMSE.12 MMSE.24 MMSE.36 MMSE.48 MMSE.60 MMSE.72
1 aaa002 aaa002 29 28 28 29 30 29 NA
2 aaa003 aaa003 30 29 30 30 30 NA NA
3 aaa005 aaa005 29 28 25 NA NA 25 NA
4 aaa024 aaa024 30 29 29 29 NA NA NA
5 aaa026 aaa026 28 30 28 27 30 30 NA
6 aaa048 aaa048 30 29 29 28 28 29 NA
使用了 dput
个 df
df <- structure(list(id = c("aaa002", "aaa003", "aaa005", "aaa024",
"aaa026", "aaa048", "aaa095", "aaa222"), id_all = c("aaa000",
"aaa002", "aaa003", "aaa005", "aaa024", "aaa026", "aaa038", "aaa048"
), MMSE.BL = c(22L, 29L, 30L, 29L, 30L, 28L, 29L, 30L), MMSE.12 = c(18L,
28L, 29L, 28L, 29L, 30L, 29L, 29L), MMSE.24 = c(NA, 28L, 30L,
25L, 29L, 28L, 29L, 29L), MMSE.36 = c(NA, 29L, 30L, NA, 29L,
27L, 26L, 28L), MMSE.48 = c(NA, 30L, 30L, NA, NA, 30L, NA, 28L
), MMSE.60 = c(NA, 29L, NA, 25L, NA, 30L, NA, 29L), MMSE.72 = c(NA,
NA, NA, NA, NA, NA, NA, NA)), class = "data.frame", row.names = c(NA,
-8L))
> df
id id_all MMSE.BL MMSE.12 MMSE.24 MMSE.36 MMSE.48 MMSE.60 MMSE.72
1 aaa002 aaa000 22 18 NA NA NA NA NA
2 aaa003 aaa002 29 28 28 29 30 29 NA
3 aaa005 aaa003 30 29 30 30 30 NA NA
4 aaa024 aaa005 29 28 25 NA NA 25 NA
5 aaa026 aaa024 30 29 29 29 NA NA NA
6 aaa048 aaa026 28 30 28 27 30 30 NA
7 aaa095 aaa038 29 29 29 26 NA NA NA
8 aaa222 aaa048 30 29 29 28 28 29 NA
我有一个 300x300 的 df。每行代表不同患者的数据,以 id 命名。前两列是患者 ID。列 'id_all' 包含的参与者多于需要,多于 'id'。我的目标是仅保留与第一列 'id'.
相对应的患者信息第一个 9x9 看起来像这样:
id | id_all | MMSE BL | MMSE 12 | MMSE 24 | MMSE 36 | MMSE 48 | MMSE 60 | MMSE 72 |
---|---|---|---|---|---|---|---|---|
aaa002 | aaa000 | 22 | 18 | NA | NA | NA | NA | NA |
aaa003 | aaa002 | 29 | 28 | 28 | 29 | 30 | 29 | NA |
aaa005 | aaa003 | 30 | 29 | 30 | 30 | 30 | NA | NA |
aaa024 | aaa005 | 29 | 28 | 25 | NA | NA | 25 | NA |
aaa026 | aaa024 | 30 | 29 | 29 | 29 | NA | NA | NA |
aaa048 | aaa026 | 28 | 30 | 28 | 27 | 30 | 30 | NA |
aaa095 | aaa038 | 29 | 29 | 29 | 26 | NA | NA | NA |
aaa222 | aaa048 | 30 | 29 | 29 | 28 | 28 | 29 | NA |
因此,基于第一列,我想以某种方式遍历第二列,并删除与第一列不匹配的参与者的所有信息,'id'. 这意味着,在第一行中,删除列 2:300,并保持第一列不变。
最后,我希望我的 df 看起来像这样:
id | id_all | MMSE BL | MMSE 12 | MMSE 24 | MMSE 36 | MMSE 48 | MMSE 60 | MMSE 72 |
---|---|---|---|---|---|---|---|---|
aaa002 | aaa002 | 29 | 28 | 28 | 29 | 30 | 29 | NA |
aaa003 | aaa003 | 30 | 29 | 30 | 30 | 30 | NA | NA |
aaa005 | aaa005 | 29 | 28 | 25 | NA | NA | 25 | NA |
aaa024 | aaa024 | 30 | 29 | 29 | 29 | NA | NA | NA |
aaa026 | aaa026 | 28 | 30 | 28 | 27 | 30 | 30 | NA |
aaa048 | aaa048 | 30 | 29 | 29 | 28 | 28 | 29 | NA |
aaa095 | ... | |||||||
aaa222 | ... |
在此示例中,id_all aaa000 和 aaa038 在 id 列中没有匹配项,因此我想删除有关这些参与者的所有信息。 我不知道如何删除几乎所有行(几乎是因为只剩下前两个单元格),以及如何将所有单元格向上移动。
另一种可能性是,将第一列向下移动直到 id 匹配 id_all,然后删除 id 列中有空单元格的整行.
谢谢!
在 tidyverse 中:
library(dplyr)
df %>%
filter(id == id_all)
基地内:
df[df$id == df$id_all, ]
我认为这会达到目的
library(tidyverse)
df %>% filter(!is.na(match(id_all, df$id))) %>% select(-id)
id_all MMSE.BL MMSE.12 MMSE.24 MMSE.36 MMSE.48 MMSE.60 MMSE.72
1 aaa002 29 28 28 29 30 29 NA
2 aaa003 30 29 30 30 30 NA NA
3 aaa005 29 28 25 NA NA 25 NA
4 aaa024 30 29 29 29 NA NA NA
5 aaa026 28 30 28 27 30 30 NA
6 aaa048 30 29 29 28 28 29 NA
由于id == id_all
在最终数据中,不需要重复的列。如果需要,可以通过在上述语法
mutate(id = id_all)
来轻松创建
df %>% filter(!is.na(match(id_all, df$id))) %>% select(-id) %>% mutate(id = id_all) %>%
select(id, everything())
id id_all MMSE.BL MMSE.12 MMSE.24 MMSE.36 MMSE.48 MMSE.60 MMSE.72
1 aaa002 aaa002 29 28 28 29 30 29 NA
2 aaa003 aaa003 30 29 30 30 30 NA NA
3 aaa005 aaa005 29 28 25 NA NA 25 NA
4 aaa024 aaa024 30 29 29 29 NA NA NA
5 aaa026 aaa026 28 30 28 27 30 30 NA
6 aaa048 aaa048 30 29 29 28 28 29 NA
使用了 dput
个 df
df <- structure(list(id = c("aaa002", "aaa003", "aaa005", "aaa024",
"aaa026", "aaa048", "aaa095", "aaa222"), id_all = c("aaa000",
"aaa002", "aaa003", "aaa005", "aaa024", "aaa026", "aaa038", "aaa048"
), MMSE.BL = c(22L, 29L, 30L, 29L, 30L, 28L, 29L, 30L), MMSE.12 = c(18L,
28L, 29L, 28L, 29L, 30L, 29L, 29L), MMSE.24 = c(NA, 28L, 30L,
25L, 29L, 28L, 29L, 29L), MMSE.36 = c(NA, 29L, 30L, NA, 29L,
27L, 26L, 28L), MMSE.48 = c(NA, 30L, 30L, NA, NA, 30L, NA, 28L
), MMSE.60 = c(NA, 29L, NA, 25L, NA, 30L, NA, 29L), MMSE.72 = c(NA,
NA, NA, NA, NA, NA, NA, NA)), class = "data.frame", row.names = c(NA,
-8L))
> df
id id_all MMSE.BL MMSE.12 MMSE.24 MMSE.36 MMSE.48 MMSE.60 MMSE.72
1 aaa002 aaa000 22 18 NA NA NA NA NA
2 aaa003 aaa002 29 28 28 29 30 29 NA
3 aaa005 aaa003 30 29 30 30 30 NA NA
4 aaa024 aaa005 29 28 25 NA NA 25 NA
5 aaa026 aaa024 30 29 29 29 NA NA NA
6 aaa048 aaa026 28 30 28 27 30 30 NA
7 aaa095 aaa038 29 29 29 26 NA NA NA
8 aaa222 aaa048 30 29 29 28 28 29 NA