就地变异和多列条件下的 if_any

问题描述 投票:0回答:1

我正在使用 R dplyr 并尝试就地改变多个列。这些列是 var1-var3,它们当前包含 1 或 NA 值。 我想应用以下逻辑:如果 var1-var3 中的给定行至少有一个值 = 1,则该行的任何 NA 值都将转换为零。 如果一行的所有列 (var1-var3) 均为 NA,则这些值将保持为 NA。 我正在尝试这个:

df <- data.frame("var1" = c(1,NA,1,NA,NA), 
              "var2" = c(NA,NA,NA,1,1),
              "var3" = c(1,NA,NA,1,NA),
              "age" = c(25,41,39,60,36) ,
              "satisfaction" = c(5,3,2,5,4)
              )

#  Output
#  var1 var2 var3 age sat
# 1    1   NA    1  25  5
# 2   NA   NA   NA  41  3
# 3    1   NA   NA  39  2
# 4   NA    1    1  60  5
# 5   NA    1   NA  36  4

df <- df %>% 
mutate_at(vars(contains('var')), ~ case_when(if_any(.x, `==`, 1), 
ifelse(is.na(.x), 0, .x ), .x) #replace NA with 0
)
r dplyr multiple-conditions mutate
1个回答
0
投票

一种解决方案,首先检查所选列中的所有值是否均为 NA,然后将

case_when()
与 {tidyr} 中的
replace_na()
结合应用:

library(dplyr)
df <- df |> 
  mutate(all_na = rowSums(!is.na(across(contains('var'))))) |> 
  mutate(across(contains('var'), ~case_when(
    all_na != 0 ~ tidyr::replace_na(.x, 0),
    all_na == 0 ~ .x
  ))) |> 
  select(-all_na)

返回:

  var1 var2 var3 age satisfaction
1    1    0    1  25            5
2   NA   NA   NA  41            3
3    1    0    0  39            2
4    0    1    1  60            5
5    0    1    0  36            4
© www.soinside.com 2019 - 2024. All rights reserved.