rdplyrpurrracrossr-glue

Using dplyr::across with two sets of variables


I have two sets of variables, for example variable a and variable a_avail. I am trying to change the value of a based on the value of a_avail and am wondering if this can be done using across with glue.

Here is what I have tried. No error is produced, but the glue does not appear to be picking up the values of .x_avail since all returned values are NA:

library(tidyverse)

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))

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

df2
#> # A tibble: 5 x 6
#>       a a_avail     b b_avail a_new b_new
#>   <dbl>   <dbl> <dbl>   <dbl> <dbl> <dbl>
#> 1     0       1     1       1    NA    NA
#> 2     1       1     1       0    NA    NA
#> 3     0       1     1       0    NA    NA
#> 4     0       0     0       1    NA    NA
#> 5     0       0     0       0    NA    NA

Created on 2021-02-12 by the reprex package (v0.3.0)


Solution

  • Ronak Shah in his answer to a related question has suggested a fantastic approach, which I am reproducing below.

    Actually two things

    Do this

    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 ~ NA_real_
                    ),
                    .names = "{.col}_new"))
    
    # A tibble: 5 x 6
          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