nice selection

By Zhian N. Kamvar in example R

June 18, 2019

I started writing in R before the tidyverse became a thing and I never really had to think about non-standard evaluation when writing functions. Those days are long past and I’ve recently struggled with the challenge when writing functions for the R4EPIs project, which would stick out like ugly little trolls along side tidyverse functions.

One of my biggest struggles was trying to figure out how, excactly to select a varaible from a user as either a character string or a bare variable. I had only known about rlang::enquo() and rlang::sym(), but I thought I had to use one or the other.

I had liked tidyselect::vars_select() because it gave me characters that I could use on my data frame columns, and it worked really will with the dots:

f <- function(.df, ...) {
  tidyselect::vars_select(colnames(.df), ...)
}
f(iris, tidyselect::starts_with("Sepal"))
##   Sepal.Length    Sepal.Width 
## "Sepal.Length"  "Sepal.Width"
f(iris, Sepal.Width)
##   Sepal.Width 
## "Sepal.Width"
f(iris, "Sepal.Width")
##   Sepal.Width 
## "Sepal.Width"

But when I would try it with specific arguments, it would scold me if the data weren’t in character form:

f <- function(.df, var) {
  tidyselect::vars_select(colnames(.df), var)
}
f(iris, Sepal.Width)
## Error: object 'Sepal.Width' not found
f(iris, "Sepal.Width")
## Note: Using an external vector in selections is ambiguous.
## ℹ Use `all_of(var)` instead of `var` to silence this message.
## ℹ See <https://tidyselect.r-lib.org/reference/faq-external-vector.html>.
## This message is displayed once per session.
##   Sepal.Width 
## "Sepal.Width"

I recently found that I could use !! enquo(var) to allow the user to input either a character or a bare variable:

library("rlang")
f <- function(.df, var) {
  tidyselect::vars_select(colnames(.df), !! enquo(var))
}
f(iris, Sepal.Width)
##   Sepal.Width 
## "Sepal.Width"
f(iris, "Sepal.Width")
##   Sepal.Width 
## "Sepal.Width"

And now it finally makes sense!

Posted on:
June 18, 2019
Length:
2 minute read, 281 words
Categories:
example R
Tags:
tidyverse tidyselect purrr R functions programming
See Also:
My life with the r-universe
Parsing GitHub Task Lists with {tinkr}
WTH is GitHub's GraphQL API even?
comments powered by Disqus