在函数内提取列属性

问题描述 投票:0回答:1

假设我有以下小故事:

df1 <- structure(list(var1 = structure(c("Didn't do a thing", "Almost did a thing", 
"Once did a thing", "Have never done a thing", "Always do a thing"
), description = "This is the question i asked respondents (and the title of the plot)"), 
    wtd_pct = c(4L, 15L, 62L, 11L, 8L)), row.names = c(NA, -5L
), class = c("tbl_df", "tbl", "data.frame"))

我想制作一个绘图函数,将小标题的名称(

df1
)和其中的列名称作为输入(在本例中,只有
var1
,但在我的实际小标题中,我有很多更多专栏)。

在绘图函数内,我想拉出连接到

var1
的属性并将其作为绘图标题。例如,在函数外部,如下所示:

df1 %>% 
  ggplot(aes(y = var1, x = wtd_pct)) +
  geom_col(aes(fill = var1)) +
  geom_text(aes(label = paste0(round(wtd_pct, 0), "%")), size = 3.5, vjust = -.5, hjust = -.3, color = 'black') +
  theme_minimal() + theme(legend.position = "none") +
  labs(y = "", 
       x = "Weighted percent", 
       title = paste0("\"", str_wrap(attr(df1$var1, "description"), 100), "\""))

注意上面的

title
行。但是,当我将其放入函数并尝试调用它时,我会遇到各种错误。例如

plot_function <- function(.x, .y){
.x %>% 
  ggplot(aes(y = {{.y}}, x = wtd_pct)) +
  geom_col(aes(fill = {{.y}})) +
  geom_text(aes(label = paste0(round(wtd_pct, 0), "%")), size = 3.5, vjust = -.5, hjust = -.3, color = 'black') +
  theme_minimal() + theme(legend.position = "none") +
  labs(y = "", 
       x = "Weighted percent", 
       title = paste0("\"", str_wrap(attr({{.x$.y}}, "description"), 100), "\""))
}

plot_function(df1, var1)

这将返回绘图,但没有标题+错误

Warning message: Unknown or uninitialised column: 
.y
.
。我尝试过各种其他方法(包装在
!!ensym()
.data[[]]
、首先将属性提取到单独的字符串中等,但我从未得到我想要的。

问题的关键似乎是你无法将 df 通过管道传输到

attr()
,但它也不喜欢
.x$.y
语法。这里有人能指出我正确的方向吗?

r ggplot2 attr
1个回答
0
投票

$
运算符使用非标准评估而不进行替换,因此
.x$.y
将被解释为“
.y
内部名为
df1
的列”,这当然不存在。

解决此问题的通常方法是使用

[[
而不是
$
,但这在这里有点棘手,因为您想要传递不带引号的列名称。

一种选择是使用

.x[[deparse(substitute(.y))]]
(不使用卷曲运算符)

plot_function <- function(.x, .y){
  .x %>% 
    ggplot(aes(y = {{.y}}, x = wtd_pct)) +
    geom_col(aes(fill = {{.y}})) +
    geom_text(aes(label = paste0(round(wtd_pct, 0), "%")), 
              size = 3.5, vjust = -.5, hjust = -.3, color = 'black') +
    theme_minimal() + theme(legend.position = "none") +
    labs(y = "", 
         x = "Weighted percent", 
         title = paste0("\"", str_wrap(attr(.x[[deparse(substitute(.y))]],
                                            "description"), 100), "\""))
}

plot_function(df1, var1)

© www.soinside.com 2019 - 2024. All rights reserved.