Ahmed Ayub Khan
Ahmed Ayub Khan

Reputation: 11

mutate_at with all_of() in r?

Trying to future proof some code here. I was unable to figure out this following warning message:

snpdata <- snpdata %>%
  mutate_at(vars(snpcol_start:snpcol_end),
            list(~ ifelse(. == 0, "AA", ifelse(. == 1, "AB", .))))

Warning messages: 1: Using an external vector in selections was deprecated in tidyselect >1.1.0. ℹ Please use all_of() or any_of() instead.

# Was: data %>% select(snpcol_start)

# Now: data %>% select(all_of(snpcol_start))

See https://tidyselect.r-lib.org/reference/faq-external-vector.html. This warning is displayed once every 8 hours.

Call lifecycle::last_lifecycle_warnings() to see where this warning was generated. 2: Using an external vector in selections was deprecated in tidyselect 1.1.0. ℹ Please use all_of() or any_of() instead.

# Was: data %>% select(snpcol_end)

# Now: data %>% select(all_of(snpcol_end))

See https://tidyselect.r-lib.org/reference/faq-external-vector.html. This warning is displayed once every 8 hours. Call lifecycle::last_lifecycle_warnings() to see where this warning was generated.

Please help, I am new to R

Upvotes: 1

Views: 171

Answers (2)

Mark
Mark

Reputation: 12518

The new syntax is this:

# sample data
snpdata <- tibble(
    snpcol_start = c(1, 0, 1),
    snpcol_end = c(0, 1, 0)
)

snpdata %>%
  mutate(across(snpcol_start:snpcol_end, \(x) ifelse(x == 0, "AA", ifelse(x == 1, "AB", x))))

I've swapped out the tilde syntax for anonymous functions for the \(x) syntax introduced in R 4.1. You can also, if you want things to be more concise (and readable), replace the nested ifelse with a case_when:

snpdata %>%
  mutate(across(snpcol_start:snpcol_end, \(x) case_when(
    x == 0 ~ "AA",
    x == 1 ~ "AB",
    TRUE ~ as.character(x)
  )))

Upvotes: 1

Rui Barradas
Rui Barradas

Reputation: 76402

Here is a solution with across, not all_of.

suppressPackageStartupMessages(
  library(dplyr)
)

set.seed(2023)
snpdata <- replicate(3, rbinom(5, 1, 0.5)) %>%
  as.data.frame() %>%
  `names<-`(paste("snpcol", c("start", "mid", "end"), sep = "_"))

snpdata %>%
  mutate_at(vars(snpcol_start:snpcol_end),
            list(~ ifelse(. == 0, "AA", ifelse(. == 1, "AB", .))))
#>   snpcol_start snpcol_mid snpcol_end
#> 1           AA         AA         AB
#> 2           AA         AA         AA
#> 3           AA         AB         AA
#> 4           AA         AA         AB
#> 5           AA         AA         AB

snpdata %>%
  mutate(across(snpcol_start:snpcol_end,
                ~ ifelse(. == 0, "AA", ifelse(. == 1, "AB", .))))
#>   snpcol_start snpcol_mid snpcol_end
#> 1           AA         AA         AB
#> 2           AA         AA         AA
#> 3           AA         AB         AA
#> 4           AA         AA         AB
#> 5           AA         AA         AB

Created on 2023-07-25 with reprex v2.0.2

A across/case_when solution is

snpdata %>%
  mutate(across(snpcol_start:snpcol_end,
                ~ case_when(
                  . == 0 ~ "AA",
                  . == 1 ~ "BB",
                  TRUE ~ as.character(.)
                )))
#>   snpcol_start snpcol_mid snpcol_end
#> 1           AA         AA         BB
#> 2           AA         AA         AA
#> 3           AA         BB         AA
#> 4           AA         AA         BB
#> 5           AA         AA         BB

Created on 2023-07-25 with reprex v2.0.2

Upvotes: 1

Related Questions