我们实际上可以将两组多个变量传递到 dplyr 中的 mutate 中吗

Ani*_*yal 3 r dplyr across

这个问题虽然有三个答案,但在我思考这个问题时却引起了我的怀疑。虽然我知道问题可以通过其他方法解决(特别是使用 purrr 或应用函数组),但我不确定它实际上可以通过吗mutate(across(...?为了清楚起见,我在这里重现这个问题。注意:我不是在寻找它的答案,而是只是对我的疑问的答案是否两组变量实际上可以通过 mutate/across 传递

有两组变量(一组没有后缀,一组有后缀avail)。

df <- tibble(a = c(0, 1, 0, 0, 0),
       a_avail = c(1, 1, 1, 0, 0),
       b = c(1, 1, 1, 0, 0),
       b_avail = c(1, 0, 0, 1, 0))
# A tibble: 5 x 4
      a a_avail     b b_avail
  <dbl>   <dbl> <dbl>   <dbl>
1     0       1     1       1
2     1       1     1       0
3     0       1     1       0
4     0       0     0       1
5     0       0     0       0
Run Code Online (Sandbox Code Playgroud)

现在,如果我们想要改变一组变量(a 和 b),但通过将它们与另一组串联进行比较。也就是说,当 a 列发生变化时,它可以使用其相应的变量 a_avail,而当 b 列发生变化时,它可以使用相应的变量,依此类推,b_avail最多可达 n 个变量。

除了 OP 之外,我已经尝试过这些代码

df %>% mutate(d = row_number()) %>%
  mutate(across(.cols = c(a_avail, b_avail),
                .fns = ~case_when(
                  .x == 1 ~ {str_replace(cur_column(), "_avail", "")[d]},
                  .x == 0 ~ NA_character_
                ),
                .names = "{.col}_new"))
Run Code Online (Sandbox Code Playgroud)

或者

df %>% 
  mutate(across(.cols = c(a, b),
                .fns = ~case_when(
                  glue::glue("{cur_column()}_avail") == 1 ~ .x,
                  glue::glue("{cur_column()}_avail") == 0 ~ as.numeric(NA)
                ),
                .names = "{.col}_new"))
Run Code Online (Sandbox Code Playgroud)

但无济于事。有人可以澄清是否可以通过 mutate(cross.. 语法来完成吗?

Ron*_*hah 5

您可以使用 with 来执行此get操作cur_column()

library(dplyr)

df %>% 
  mutate(across(.cols = c(a, b),
                .fns = ~case_when(
                  get(glue::glue("{cur_column()}_avail")) == 1 ~ .x,
                  get(glue::glue("{cur_column()}_avail")) == 0 ~ as.numeric(NA)
                ),
                .names = "{.col}_new"))

#      a a_avail     b b_avail a_new b_new
#  <dbl>   <dbl> <dbl>   <dbl> <dbl> <dbl>
#1     0       1     1       1     0     1
#2     1       1     1       0     1    NA
#3     0       1     1       0     0    NA
#4     0       0     0       1    NA     0
#5     0       0     0       0    NA    NA
Run Code Online (Sandbox Code Playgroud)

PS - 我不确定这是否应该是您链接的帖子的答案。