Last active
April 12, 2019 13:30
-
-
Save paullemmens/e518d997160927459cb847c87eeb1bf2 to your computer and use it in GitHub Desktop.
rlang, tidyeval, dplyr, ggplot and non-syntactic column names
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
## I have a data set something like this. | |
mtc <- mtcars %>% | |
mutate(cyl = factor(cyl), | |
gear = factor(gear), | |
`Q17_anx/worry about abc` = gear, | |
`Q17_anx about abc` = gear) | |
## An admittedly ugly function (on various levels / from diverse perspectives) | |
## in which I'm trying baby steps for tidy evaluation. | |
ppp <- function(dfr, q, by = NULL, n.resp = length(unique(dfr$cyl))) { | |
grp <- rlang::syms(q) | |
response <- rlang::ensym(q) | |
## count answered and skipped. | |
skipped <- dfr %>% filter(is.na(!!!grp)) %>% count(!!!grp) %>% pull(n) | |
N <- n.resp - skipped | |
if (!is.null(by)) { | |
grp <- rlang::syms(list(q, by)) | |
} | |
d <- dfr %>% | |
filter(!is.na(!!response)) %>% | |
count(!!!grp) | |
if (!is.null(by)) { | |
b <- rlang::ensym(by) | |
d <- d %>% | |
group_by(!!b) %>% | |
mutate(N = sum(n)) | |
} else { | |
d <- d %>% mutate(N = sum(n)) | |
} | |
d <- d %>% | |
mutate(perc = n/N) | |
N <- sum(d$n) | |
p <- d %>% | |
ggplot(mapping = aes(x = !!response, y = perc, colour = !!response, fill = !!response)) + | |
geom_col() + | |
labs(x = '', y = '') + | |
scale_y_continuous(limits = range(0, 1), breaks = seq(0, 1, 0.10), labels = scales::percent) + | |
scale_x_discrete(limits = rev(levels(d[[q]]))) + | |
coord_flip() + | |
guides(fill = FALSE, colour = FALSE) + | |
theme_bw() + | |
theme(strip.background = ggplot2::element_rect(colour = NA, fill = NA)) | |
if (!is.null(by)) p <- p + facet_wrap(as.formula(paste('~', by))) | |
return(p) | |
} | |
## Then I'm calling the function like this. | |
mtc %>% ppp(q = 'cyl', by = 'gear') # Works | |
mtc %>% ppp(q = 'cyl', by = 'Q17_anx/worry about abc') # ERROR (unexpected symbol) | |
mtc %>% ppp(q = 'cyl', by = 'Q17_anx about abc') # ERROR ibid | |
## Error for the last above call: | |
## Error in parse(text = x, keep.source = FALSE) : | |
## <text>:1:11: unexpected symbol | |
##1: ~ Q17_anx about | |
## ^ |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
On twitter @_lionelhenry said
You need
facet_wrap(vars(!!by))
.If your function is meant to take strings, I wouldn't use NSE in its interface at all. Just use
sym()
andsyms()
to transform to symbols. Or pass the raw strings directly to.data[[
, that's a bit safer:facet_wrap(vars(.data[[by]]))