Reputation: 182
I would like to replace value of df1 by two vector(g1.vec. g2.vec) and column group
.
If column of df1 exitst g1.vec and group == 1, replace value to Y. If column of df1 exitst g2.vec and group == 2, replace value to X. Here is a part of example:
> df1
ID group col1 col2 ...... col154
1 AMM115 2 C A ...... A+
2 ADM107 1 NA NA ...... B
3 AGM041 2 B C ...... C+
4 AGM132 1 A NA ...... A+
5 AQM007 1 NA A ...... B+
6 ARM028 2 NA B+ ...... A-
7 ASM019 1 A A+ ...... NA
8 AHM172 NA A A+ ...... NA
> vec
g1.vec <- c("col1", "col3", "col18", "col20", "col28", "col75", "col77", "col86", "col111")
g2.vec <- c("col2", "col13", "col37", "co38", "co44", "co87", "col123", "col41", "col154")
the output would look like:
> df2
ID group col1 col2 ...... col154
1 AMM115 2 C X ...... X
2 ADM107 1 Y NA ...... B
3 AGM041 2 B X ...... X
4 AGM132 1 Y NA ...... A+
5 AQM007 1 Y A ...... B+
6 ARM028 2 NA X ...... X
7 ASM019 1 Y A+ ...... NA
8 AHM172 NA A A+ ...... NA
What I have tried mutate
with ifelse
but I do not know how to mutate multiples column once or whatever to complete this.
df1 <- structure(list(ID = c("AMM115", "ADM107", "AGM041", "AGM132",
"AQM007", "ARM028", "ASM019", "AHM172"), group = c(2L, 1L, 2L,
1L, 1L, 2L, 1L, NA), col1 = c("C", NA, "B", "A", NA, NA, "A",
"A"), col2 = c("A", NA, "C", NA, "A", "B+", "A+", "A+"), col154 = c("A+",
"B", "C+", "A+", "B+", "A-", NA, NA)), class = "data.frame", row.names = c("1",
"2", "3", "4", "5", "6", "7", "8"))
Upvotes: 1
Views: 96
Reputation: 887951
Using across
and case_match
from dplyr
library(dplyr)# version 1.1.0
df1 %>%
mutate(across(any_of(g1.vec),~ case_match(group, 1 ~ 'Y', .default = .x)),
across(any_of(g2.vec), ~ case_match(group, 2 ~ 'X', .default = .x)))
-output
ID group col1 col2 col154
1 AMM115 2 C X X
2 ADM107 1 Y <NA> B
3 AGM041 2 B X X
4 AGM132 1 Y <NA> A+
5 AQM007 1 Y A B+
6 ARM028 2 <NA> X X
7 ASM019 1 Y A+ <NA>
8 AHM172 NA A A+ <NA>
Upvotes: 2
Reputation: 15153
You may try
library(dplyr)
df1 %>%
mutate_at(g1.vec, list(~ifelse(group == 1 & !is.na(group), 'Y', .))) %>%
mutate_at(g2.vec, list(~ifelse(group == 2 & !is.na(group), 'X', .)))
Upvotes: 2
Reputation: 389325
Base R solution -
df[df$group %in% 1, g1.vec] <- 'Y'
df[df$group %in% 2, g2.vec] <- 'X'
df
# ID group col1 col2 col154
#1 AMM115 2 C X X
#2 ADM107 1 Y <NA> B
#3 AGM041 2 B X X
#4 AGM132 1 Y <NA> A+
#5 AQM007 1 Y A B+
#6 ARM028 2 <NA> X X
#7 ASM019 1 Y A+ <NA>
#8 AHM172 NA A A+ <NA>
I have used %in%
instead of ==
here to handle the NA
values.
Upvotes: 3